Code Fix

中級

0.1 + 0.2 === 0.3 がfalseになる理由と直し方

浮動小数点数は2進数で表現されるため、0.1や0.2のような10進の小数を正確に表せません。演算結果はごくわずかな誤差を含み、===での比較は失敗します。

なぜエラーが出ないのか

出力: false
(エラーなし)
JavaScriptは何も報告しません。文法として正しいためです
出力: false
実際の挙動 — 期待した結果と食い違っている箇所
見つけ方
エラーが出ないので、出力を目で確かめるか、コードを目で追うしかありません。この種の誤りが最も発見が遅れます

このエラーが出る典型パターン

パターン1

 1  const price = 0.1 + 0.2;
 2  console.log(price === 0.3                         );
                                   ^
出力: false期待: true (エラーにはなりません)

0.1と0.2は2進数の浮動小数点数として正確に表せないため、加算結果はわずかに0.3からずれます。厳密な===ではなく、誤差の範囲で比較する必要があります。

直し方: price === 0.3Math.abs(price - 0.3) < Number.EPSILON にします。

この問題を解いてみる →

広告
広告スロット(未設定)

パターン2

 1  const total = 1 - 0.9;
 2  console.log(total === 0.1                         );
                                   ^
出力: false期待: true (エラーにはなりません)

1 - 0.9も浮動小数点の誤差で0.1と厳密には一致しません。減算でも加算と同じ問題が起こります。

直し方: total === 0.1Math.abs(total - 0.1) < Number.EPSILON にします。

この問題を解いてみる →

パターン3

 1  const sum = 0.1 * 3;
 2  console.log(sum === 0.3                         );
                                  ^
出力: false期待: true (エラーにはなりません)

掛け算でも同じ誤差が生じます。0.1 * 3は0.30000000000000004になり、0.3とは===で一致しません。

直し方: sum === 0.3Math.abs(sum - 0.3) < Number.EPSILON にします。

この問題を解いてみる →

よくある誤解

「小数の計算は正確なはず」という前提はJavaScriptに限らずほとんどの言語の浮動小数点数に当てはまりません。厳密な一致ではなく、Number.EPSILONのような小さな許容誤差の範囲で比較する必要があります。

まとめ

0.1 + 0.2 === 0.3 がfalseになる理由と直し方は中級でつまずきやすい項目です。上の3パターンを実際に手で直すと、エラーメッセージのどこを読めばよいかが掴めます。

演習をはじめる

関連するエラー

広告
広告スロット(未設定)