Frage

Warum ist q == 0 im folgende Skript?

<script>
  var start = 1234567890123456789;
  var end =   1234567890123456799;
  var q = end - start;
  alert(q);
</script>

Ich würde denken, sollte das Ergebnis 10 sein Was ist der richtige Weg, diese beiden Zahlen zu subtrahieren?

War es hilfreich?

Lösung

Da Zahlen in JavaScript sind Gleitkommazahlen. Sie haben begrenzte Genauigkeit.

Wenn Sie JavaScript eine sehr lange Zahl sieht, rundet es auf die nächste Zahl es als 64-Bit-Float darstellen kann. In Ihrem Skript, start und end get gerundet auf den gleichen Wert.

alert(1234567890123456789);   // says: 1234567890123456800
alert(1234567890123456799);   // says: 1234567890123456800

Es gibt keine integrierte Möglichkeit, präzise Arithmetik auf große ganzen Zahlen zu tun, aber Sie können eine BigInteger Bibliothek wie dieses .

Andere Tipps

Jason veröffentlicht bereits das Warum. // www-: Für eine Lösung, können Sie eine Javascript-Bibliothek BigInt unter http bekommen cs-students.stanford.edu/~tjw/jsbn/

const subtract = (a, b) => [a, b].map(n => [...n].reverse()).reduce((a, b) => a.reduce((r, d, i) => {
    let s = d - (b[i] || 0)
    if (s < 0) {
        s += 10
        a[i + 1]--
    }
    return '' + s + r
}, '').replace(/^0+/, ''))


Bessere Nutzung big-Integer-Bibliothek für diese Dinge, um alle verschiedenen Testfälle zu behandeln.

Dies ist nur für den allgemeinen Fall, dass Sie verwenden können ....

Es wird erklärt, in der JavaScript Dokumentation :

  

Nach dem ECMAScript-Standard, gibt es nur eine Zahl Typ: doppelte Genauigkeit 64- Bit-binär-Format IEEE 754-Wert (Zahlen zwischen -(2 53 und -1) 2 53 -1). Es gibt keinen speziellen Typ für ganze Zahlen.

Wikipedia-Seite über double precision floating point Format erklärt:

  

Zwischen 2 52 = 4,503,599,627,370,496 und 2 53 = 9,007,199,254,740,992 die darstellbaren Zahlen sind genau die Zahlen. Für den nächsten Bereich, von 2 53 bis 2 54 , alles wird durch 2 multipliziert, so dass die darstellbaren Zahlen sind die geraden, etc.

(Alle ganzen Zahlen kleiner als 2 52 sind genau dargestellt.)

1234567890123456789 und 1234567890123456799 sind größer als 2 60 = 1152921504606846976. Bei dieser Größenordnung nur etwa 1% der ganzen Zahlen gespeichert ist genau doppelte Genauigkeit unter Verwendung von Fließkommaformat.

Diese können zwei nicht genau gespeichert werden. Beide sind gerundet auf 1234567890123456800.


JavaScript Dokumentation erklärt auch, wie man sagen, wenn ein eine ganze Zahl gespeichert ist, genau:

  

[...] und beginnend mit ECMAScript 6, Sie sind auch in der Lage zu überprüfen, ob eine Zahl in doppelter Genauigkeit ist Gleitkommazahl Bereich mit Number.isSafeInteger() sowie Number.MAX_SAFE_INTEGER und Number.MIN_SAFE_INTEGER . Außerhalb dieses Bereichs, ganze Zahlen in JavaScript sind nicht mehr sicher und werden eine Doppel-precision floating point Annäherung des Wertes sein.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top