問題
JavaScript では、整数と浮動小数点数の両方が Number データ型 (単純なデータ型の 1 つ) に属します。1.0 などの浮動小数点数を出力すると、結果が 1 ではなく 1 になることがよくあります。 1.0。これは、浮動小数点数を保存するためです。ポイントは整数値を格納する場合に比べて 2 倍のメモリを消費するため、ECMAScript は浮動小数点数を整数に変換するのに時間を無駄にしません。
上記の状況は強迫性障害の患者を少し不快にさせますが、いずれにしても、それは大きな間違いではありません、次の状況は非常に恐ろしいものになるでしょう。たとえば、0.1 + 0.2 を計算すると、出力結果は 0.3 ではなく、0.3000000000000004 になります。何だ? !初めてこのような状況に遭遇した子どもたちにとって、あなたの世界観は挑戦されたと感じますか?
原因
そこで、私は魂と体を救うためにすぐに本を開いたところ、その本にはっきりと書かれていることがわかりました: ECMAScrip は IEEE754 の数値浮動小数点計算に基づいています。IEEE754 が何なのかわからない場合は、ただ説明してください。この数値計算方法は、値を 2 進数で保存してから計算を実行します。浮動小数点数は 2 進数で表現すると無限大になるため、四則演算の際に丸め誤差が発生します。整数の計算よりも精度が低くなります。最後に、特定の浮動小数点数の値を決してテストしないでください。
つまり、若者は教育を受けていないと、常に人生に疑問を抱くので、もっと勉強する必要がある、という楊江氏の言葉は正しいのです。 ! !
解決策
いわゆる、適切な薬を処方する、問題の原因がわかれば、問題の解決策を見つけることができます。これは浮動小数点数の 2 進数が無限であるために発生するエラーなので、このエラーは整数演算には存在しません。真実を理解できるほど賢明ですか?そう、それは算術工学において浮動小数点数を整数に変換し、その結果を浮動小数点数に変換することです。ゲストオフィサー、以下が新しいコードです~
//加法 function FloatAdd(arg1,arg2){ var r1,r2,m; try{r1=arg1.toString().split(".")[1].length}catch(e){r1=0; //参数1为整数}; //参数1小数点后的位数 try{r2=arg2.toString().split(".")[1].length}catch(e){r2=0; //参数2为整数}; //参数2小数点后的位数 m=Math.pow(10,Math.max(r1,r2)); //取其中较大的位数 return (arg1*m+arg2*m)/m; //先将arg1和arg2转换为整数进行计算,然后再转换回浮点数 }