先日、こんなツイートを見かけました。
見ろよ,これがJavaScript pic.twitter.com/ELVlDGAOq0
— プログラミングヤクザ v2.0 (@prog893) 2017年8月1日
NaNってなんだっけ?
どっかで見た記憶があるけどなんだっけなー。
なるほど。非数。
ついでにIEEE754についてもWikiレベルで確認。
しかし「数字ではないもの」と「数字ではないもの」は、必ずしも同一ではない、っていう理屈では。
— 都元ダイスケ🍅 (@daisuke_m) 2017年8月2日
解釈は納得。
NaNはJavaでも定義されている様です。
JavaScriptと同様に==
ではfalse
となるのかが気になります。また、==
では常にfalse
となる理由が気になるので少し調べてみました。
NaNとか意識したことないから、とりあえず比較してみました。
Double nan1 = Double.NaN; Double nan2 = Double.NaN; if(nan1 == nan2) System.out.println("nan1 == nan2 => true"); if(nan1.equals(nan2)) System.out.println("nan1.equals(nan2) => true"); if(nan1.doubleValue() == nan2.doubleValue()) System.out.println("nan1.doubleValue() == nan2.doubleValue() => true"); System.out.println("Double.doubleToLongBits(nan1) => " + Double.doubleToLongBits(nan1)); System.out.println("Double.doubleToLongBits(nan2) => " + Double.doubleToLongBits(nan2)); System.out.println("nan1.hashCode() => " + nan1.hashCode()); System.out.println("nan2.hashCode() => " + nan2.hashCode());
nan1.equals(nan2) => true Double.doubleToLongBits(nan1) => 9221120237041090560 Double.doubleToLongBits(nan2) => 9221120237041090560 nan1.hashCode() => 2146959360 nan2.hashCode() => 2146959360
==
での比較はfalse
になるけど、equals()
を使うとtrue
となる、と。
なんなんでしょう、まったく。意味がわからないです。
equals()
の結果がtrue
となるのは仕様のようです。
Javaの言語規格で==
について調べてみました。
If either operand is NaN, then the result of == is false but the result of != is true.
Indeed, the test x!=x is true if and only if the value of x is NaN.
The methods Float.isNaN and Double.isNaN may also be used to test whether a value is NaN.
引用元:http://docs.oracle.com/javase/specs/jls/se8/html/jls-15.html#jls-15.21.1
NaNの==
での比較結果は無条件でfalse
となると解釈しました。
これはJavaScriptでも同様なようですね。
MATLABでも同じように記載されています。
NaNであるかのチェックは大体は、isNaN()
を使いましょうというのが常識なようです。
NaNがなんなのか知ることができて、スッキリしました。NaNの扱いについては言語が変わっても統一されているようですね。(当然か)