indexOf(NaN)が常に-1を返し、NaNを見つけられない理由
Array.prototype.indexOfは===(厳密等価)で要素を探すため、自分自身とも等しくないNaNを絶対に見つけられません。includes()はSameValueZeroというNaNを特別扱いするアルゴリズムを使うため、NaNも正しく検出できます。
なぜエラーが出ないのか
出力: -1
(エラーなし)- JavaScriptは何も報告しません。文法として正しいためです
出力: -1- 実際の挙動 — 期待した結果と食い違っている箇所
見つけ方- エラーが出ないので、出力を目で確かめるか、コードを目で追うしかありません。この種の誤りが最も発見が遅れます
このエラーが出る典型パターン
パターン1
1 const values = [1, NaN, 3]; 2 console.log(values.indexOf (NaN)); ^
出力: -1期待: true (エラーにはなりません)
indexOfは===で比較するため、自分自身とも等しくないNaNを絶対に見つけられません。includes()はNaNを特別扱いするSameValueZeroで比較するため正しく検出できます。
直し方: indexOf を includes にします。
広告
広告スロット(未設定)
パターン2
1 const readings = [12, NaN, 8]; 2 console.log(readings.indexOf (NaN)); ^
出力: -1期待: true (エラーにはなりません)
配列の途中にあってもindexOfはNaNを見つけられません。includes()を使う必要があります。
直し方: indexOf を includes にします。
パターン3
1 const samples = [NaN, 5, 9]; 2 console.log(samples.indexOf (NaN)); ^
出力: -1期待: true (エラーにはなりません)
配列の先頭であってもindexOfはNaNを見つけられません。includes()を使う必要があります。
直し方: indexOf を includes にします。
よくある誤解
「配列に含まれているかを調べるならindexOfでもincludesでも同じはず」という思い込みは、NaNが絡む場面では成り立ちません。NaNの検出だけはincludesでなければ正しく動きません。
まとめ
indexOf(NaN)が常に-1を返し、NaNを見つけられない理由は上級でつまずきやすい項目です。上の3パターンを実際に手で直すと、エラーメッセージのどこを読めばよいかが掴めます。