从办公室的勾心斗角看JS隐式类型转换

610 阅读2分钟

背景

有天上班,隔壁同事老黄在chrome控制台下输入了console.log(a == 1 && a == 2 && a == 3),在光标闪动之际问我,你能不能定义一个变量a,让这个语句打印出true。

我心想,这家伙不好好上班,在这瞎折腾,还搞个这么长而且有点匪夷所思的表达式让我去猜,肯定是想考我,并且在我解不出的时候笑话憨厚老实的我。

这时周围几位同事也围了过来看热闹,此时我内心十分紧张,额头冒出了细小的汗珠,眼睛盯着屏幕上的题目,但脑子里想到的确是解不出来时被同事取笑的情景。

冷静过后,我渐渐发现这题的端倪,里面用的都是非严格相等(==),脑子突然一激灵,想到在进行非严格相等对比时,不同类型的变量是会进行隐式类型转换的。想到这,我嘴角轻轻上扬,清了清嗓子后,就开始对周围的人JJYY了起来。

Abstract Equality Comparison

先来看看非严格相等。

在用非严格相等对比两个变量时,对于类型不一致的情况,会进行隐式类型转换。转换规则如下图。

相信大家看完之后心里在骂娘,下面我来总结一下:

这里的2、3、6、12是四个比较特殊场景。

而剩下的都遵循如下的一个逻辑。

既进过一系列的转换之后,会变成类型相同的严格相等来对比。

ToPrimitive & ToNumber

在上面,比较重要的就是ToPrimitiveToNumber这两个东西了,下面来进一步了解一下他们是如何定义的。

ToPrimitive

从这里可以看出,要了解ToPrimitive,需要进一步了解 OrdinaryToPrimitive 。
而这里大致我们可以理解为,对于对象,我们会先后调用其valueOf、toString方法,直到其中一个返回非Object类型。

ToNumber

对于ToNumber就不过多地去了解学习了。看张图找找感觉就好。

最后

讲完,我就在控制台敲下了console.log = () => true;,之后就默默的回到工位上工作了。