ホームページ > 記事 > ウェブフロントエンド > JS の型変換の落とし穴について説明しましょう
なぜこんなことを言うのですか?
面接での 1 つの質問が、私にそれを言う動機を与えてくれました。
質問は次のとおりです:
結果は真実です! ! !
実際、型変換、演算子の優先順位、これらはすべて最も基本的なものです。
サイの本には詳しい紹介があります。しかし、Rhino の本の最初の 5 章を読むことはめったにありません。 。 。
例えば優先順位については、多くの本で「優先順位を覚える必要はありません。分からない場合は括弧を追加すれば大丈夫です。」と教えられています。
私たちは通常、コードを書くときにこれを行います。
しかし、現実はどうなのでしょうか?面接ではこのような質問がされ、それに答えるように求められます。 。 。
この質問の意味がよくわかりません。 。 。
この記事では、型変換の問題を解決し、「JS 決定版ガイド」の 49 ページにある表を暗記しようとします。
どんなものが偽物ですか?
合計6つ:
var bool = new Boolean(false); if (bool) { alert('true'); } else { alert('false'); }
上記の順序は基本的なタイプに従って並べられています。
他には何もありません! !
0或+0、-0,NaN "" false undefined null
if (a && b) の形式であっても、それを理解するための正しい方法は次のとおりです: a && b は式を評価し、それをブール型に変換します。
&& は短絡構文であり、評価後は必ずしもブール型である必要はなく、ましてや両側をブール値に変換して演算を実行する必要はありません。
たとえば、2&&3 の結果は 3 ですが、これは真実ではありません。
つまり、if(a && b) という、私たちが通常理解している「a と b が同時に真である場合」は、それを説明する間違った方法です。
他の基本型を文字列に変換します、基本的に期待どおりです:
Infinity '0'、'false'、" "(空格字符) 任何引用类型:[],{},function(){}
他の基本型を数値に変換します、これには特別なメモリが必要です:
console.log("" + null); // "null" console.log("" + undefined); // "undefined" console.log("" + false); // "false" console.log("" + true); // "true" console.log("" + 0); // "0" console.log("" + NaN); // "NaN" console.log("" + Infinity); // "Infinity"
ここで、null、空の文字は 0、未定義は NaN です。
上記では、基本的な型変換についてわかりやすく説明しています。
参照型を基本型に変換する方法を見てみましょう。
参照型はブール値に変換され、常に true
参照型は文字列に変換されます
console.log(+null); // 0 console.log(+undefined); // NaN console.log(+false); // 0 console.log(+true); // 1 console.log(+""); // 0 console.log(+'1'); // 1 console.log(+'1x'); // NaN
参照型はnumberに変換されます
1.优先调用toString方法(如果有),看其返回结果是否是原始类型,如果是,转化为字符串,返回。 2.否则,调用valueOf方法(如果有),看其返回结果是否是原始类型,如果是,转化为字符串,返回。 3.其他报错。
まず、一般的な参照型 toString と valueOf が何を返すかを見てみましょう。
1.优先调用valueOf方法(如果有),看其返回结果是否是基本类型,如果是,转化为数字,返回。 2.否则,调用toString方法(如果有),看其返回结果是否是基本类型,如果是,转化为数字,返回。 3.其他报错。
したがって、文字列と数値への対応する変換は次のようになります:
var a = {}; console.dir(a.toString()); // "[object Object]" console.dir(a.valueOf()); // 对象本身 var b = [1, 2, 3]; console.dir(b.toString()); // "1,2,3" console.dir(b.valueOf()); // 对象本身 var c = [[1],[2]]; console.dir(c.toString()); // "1,2" console.dir(c.valueOf()); // 对象本身 var d = function() {return 2}; console.dir(d.toString()); // "function() {return 2}" console.dir(d.valueOf()); // 对象本身
別のエラー状況:
var a = {}; console.dir(a + ""); // "[object Object]" console.dir(+a); // NaN var b = [1, 2, 3]; console.dir(b + ""); // "1,2,3" console.dir(+b); // NaN var c = [[1],[2]]; console.dir(c + ""); // "1,2" console.dir(+c); // NaN var d = function() {return 2}; console.dir(d + ""); // "function () {return 2}" console.dir(+d); // NaN
上記の型変換ルールは基本的に完了です。
最後に、邪悪な「==」について話しましょう
面接の質問は次のとおりです:
var a = {}; a.toString = function() {return {};} console.log("" + a); // 报错 console.log(+a) // 报错
true が出てくると思いました。なんと、それはなぜ嘘なのですか?
はは。 。 。
二重等号、両側の型が異なる場合、暗黙的な変換が発生します。 Rhino の本の 75 ページでは、次のように要約されています:
var a = false; var b = undefined; if (a == b) { alert('true'); } else { alert('false'); }
したがって:
1,null和undefined,相等。 2,数字和字符串,转化为数字再比较。 3,如果有true或false,转换为1或0,再比较。 4,如果有引用类型,优先调用valueOf。 5,其余都不相等。
0 == false それが真である理由は項目 3 に基づいています。
第3条により「" == false」が真となる理由は、第2条により「" == 0」となります。
記事 4 の別の例:
console.log(undefined == false); // false console.log(null == false); // false console.log(0 == false); // true console.log(NaN == false); // false console.log("" == false); // true
上記の結果は次の理由から当てはまります:
[[2]] の valueOf はオブジェクト自体であり、基本型ではありません。
toString を呼び出そうとした結果は「2」です。
つまり、「2」と数字の2の比較になります。第 2 条によれば、平等です。なんと!!
最後に、「===」を使用すると、これらの問題が解決されます。
この記事は終わりです。