Wissenschaftliches Format als exakten Dezimalwert darstellen

  • VB.NET
  • .NET (FX) 4.5–4.8

Es gibt 8 Antworten in diesem Thema. Der letzte Beitrag () ist von RodFromGermany.

    Wissenschaftliches Format als exakten Dezimalwert darstellen

    Hey,
    Meine Frage:
    Kann man einen (bearbeiteten) größeren Double-Wert, der bei einer Ausgabe automatisch
    im wissenschaftlichen Format angezeigt wird, auch exakt als Dezimalwert ausgeben lassen?
    Vereinfachtes Beispiel:
    Dim Value As Double = Int64.MaxValue
    ' --- Hier muss Value zur Bearbeutung vom Typ Double sein!
    Label1.Text = Value.ToString ' Ergebnis: 9.2233720368547E+18
    Ich möchte allerdings folgende Ausgabe haben: 9223372036854775807
    Keine Alternative für mich ist:
    Dim Value As Int64 = Int64.MaxValue
    Das würde natürlich funktionieren, kommt aber aus verschiedenen Gründen nicht In Frage!
    Auch funktioniert nicht:
    Dim NewVal as int64 = CType(Value, Int64) ' -> Fehler: "Dividieren Sie nicht durch 0"

    Weiss jemand eine Lösung?
    mfG DHB

    Ich meine:
    :P Es sollten nur ernstzunehmende Beiträge eingestellt werden!
    :( Beiträge, die nur deren Anzahl in die Höhe treiben sollen, stehlen Lesern deren Zeit und schenken nur Frust.
    ;) Wenn ein Autor sein Thema für erledigt hält, sollte er dies kurz als letzten Eintrag vermerken.
    8) Leser wüssten dann, dass hier weitere Beiträge nicht mehr sinnvoll sind.
    Die Präzision vom Datentyp Double reicht mMn nicht für wissenschaftliche Berechnungen aus, unter anderem deswegen werden soweit ich weiß auch die letzten Dezimalstellen mit der ​E+/-n-Form abgekürzt. Ein Decimal wäre hier vielleicht besser geeignet.
    In C / C++ gibt es noch den Typ long double, das sind 80 Bit, also die Breite des Arithmetik-Prozessors, ist also "schmaler" als Decimal, jedoch schneller.

    DHB schrieb:

    Dim NewVal as int64 = CType(Value, Int64) ' -> Fehler: "Dividieren Sie nicht durch 0"
    Mit welchem Wert von Value kommt denn dieser Fehler (0 funktioniert bei mir)? Ich kann das leider zum Glück nicht reproduzieren.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    Hey,
    danke zunächst für Euer Feedback. Ich werde mein Problem mal präzisieren:

    VB.NET-Quellcode

    1. Dim Value As Int64 = Int64.MaxValue
    2. Dim Basis As Integer = 20
    3. Dim Exp As Double = Math.Log(Value) / Math.Log(Basis)
    4. Dim Result As Int64 = Basis ^ Exp
    5. Label1.Text = "MaxValue (" & "Int64" & "): " & Value.ToString
    6. Label2.Text = "Exponent (zur Basis " & Basis.ToString & "): " & Exp.ToString
    7. Label3.Text = "Int64-Result: " & Result.ToString

    In diesem Beispiel sollte in Label1 und Label3 der selbe Wert angezeigt werden.
    Bei allen für mich relevanten DatenTypen geschieht das auch, allerdings nicht
    bei Int64, wie im oberen Beispiel dargestellt. Aus diesem Grunde hatte ich den
    Typ für Value und Result in Double verwendet, wonach die (zumindest wissen-
    schaftlichen) Werte wieder überein stimmten. Aber offensichtlich stimmen bei
    dieser Methode die Werte nur scheinbar überein.
    Wenn Ihr dazu eine Idee habt - nur zu!

    @RodFromGermany
    Um Deine Frage noch zu beantworten; bei mir wird der Fehler nach den Zeilen

    VB.NET-Quellcode

    1. Dim Value As Double = Int64.MaxValue
    2. Dim NewVal As Int64 = CType(Value, Int64)

    ausgelöst.
    Ersetzt man Int64.MaxValue z.B. durch Int16.MaxValue, dann wird der Fehler
    nicht ausgelöst!

    mfG DHB

    Ich meine:
    :P Es sollten nur ernstzunehmende Beiträge eingestellt werden!
    :( Beiträge, die nur deren Anzahl in die Höhe treiben sollen, stehlen Lesern deren Zeit und schenken nur Frust.
    ;) Wenn ein Autor sein Thema für erledigt hält, sollte er dies kurz als letzten Eintrag vermerken.
    8) Leser wüssten dann, dass hier weitere Beiträge nicht mehr sinnvoll sind.

    Dieser Beitrag wurde bereits 3 mal editiert, zuletzt von „DHB“ ()

    @DHB Fang an mit Option Strict On: Basis ^ Exp ist ein Double.
    Die Übereinstimmung auf 15,5 Stellen finde ich gut, da Potenzrechnung bezüglich der Genauigkeit begrenzt ist.
    ------------------------
    @DHB Bei mir wird da völlig korrekt der Fehler
    Ein Ausnahmefehler des Typs "System.OverflowException" ist in WindowsApplication1.exe aufgetreten.
    Zusätzliche Informationen: Die arithmetische Operation hat einen Überlauf verursacht.
    ausgelöst.
    Klar auch, wenn man sich die Werte mal anschaut, insbesondere unter der erücksichtigung, dass ein Long mehr signifikante Stellen hat als ein Double, da wird irgendwo gerundet. In diesem Fall auf:

    Value = 9223372036854780000
    Int64.MaxValue = 9223372036854775807
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „RodFromGermany“ ()

    Hey RodFromGermany,
    es ist mir alles einleuchtend, was Du da gepostet hast.
    Ich weiß wohl, dass
    Basis ^ Exp
    ein Double ist, aber ich
    suchte eben nach einer Lösung, die mir
    1. ein exaktes Ergebnis anzeigt und
    2. bei einem Exp = 63 oder 64 keine Fehlermeldung generiert.

    VB.NET-Quellcode

    1. ' --- Ini und Ausgabe des Wertes ---
    2. Dim Value As Int64 = Int64.MaxValue
    3. Label1.Text = "int64.MaxValue: " & Value.ToString
    4. ' --- Berechnen und Ausgabe des Exp zur Basis 'n'
    5. Dim Basis As Integer = 63
    6. Dim Exp As Double = Math.Log(Value) / Math.Log(Basis)
    7. Label2.Text = "Exp zur Basis " & Basis.ToString & ": " & Exp.ToString
    8. ' --- Int64-Result: Fehlermeldung bei Exp > 62 ---
    9. Dim IResult As Int64 = Basis ^ Exp
    10. Label3.Text = "Result als Int64 berechnet: " & IResult.ToString
    11. ' --- Double-Result: Keine exakte Wert-Anzeige ---
    12. Dim DResult As Double = Basis ^ Exp
    13. Label4.Text = "Result als Double berechnet: " & DResult.ToString
    14. ' --- Und warum geht auch DAS nicht? ---
    15. Dim CResult As Decimal = Basis ^ Exp
    16. Label5.Text = "Result als Dezimal berechnet: " & CResult.ToString

    Hast Du dafür einen Lösungsvorschlag?
    mfG DHB

    Ich meine:
    :P Es sollten nur ernstzunehmende Beiträge eingestellt werden!
    :( Beiträge, die nur deren Anzahl in die Höhe treiben sollen, stehlen Lesern deren Zeit und schenken nur Frust.
    ;) Wenn ein Autor sein Thema für erledigt hält, sollte er dies kurz als letzten Eintrag vermerken.
    8) Leser wüssten dann, dass hier weitere Beiträge nicht mehr sinnvoll sind.

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „DHB“ ()

    Hey, ich hab's!
    Nach Verweis auf "System.Numerics" habe ich die Structure "BigInteger"
    benutzt, also die Result-Berechnung durch die Zeile(n) ersetzt:

    VB.NET-Quellcode

    1. Dim BResult As System.Numerics.BigInteger = Basis ^ Exp
    2. Label6.Text = "Result als BigInteger berechnet: " & BResult.ToString

    Danke nochmal für Euren Einsatz!
    mfG DHB

    Ich meine:
    :P Es sollten nur ernstzunehmende Beiträge eingestellt werden!
    :( Beiträge, die nur deren Anzahl in die Höhe treiben sollen, stehlen Lesern deren Zeit und schenken nur Frust.
    ;) Wenn ein Autor sein Thema für erledigt hält, sollte er dies kurz als letzten Eintrag vermerken.
    8) Leser wüssten dann, dass hier weitere Beiträge nicht mehr sinnvoll sind.

    DHB schrieb:

    BigInteger
    Wenn Du damit rechnest, sei Dur bewusst, dass sämtliche Berechnungen deutlich länger dauern als mit den Arithmetik-Prozessor-abbildbaren Datentypen.
    Wenn Du also komplexe Berechnungen durchführst, plane etwas mehr Zeit ein. ;)
    Vielleicht machst Du mal einen Vergleich BigInteger gegen Double und postest Deine Ergebnisse. Das dürfte auch andere User interessieren.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!