== 让TA拥有多重身份

175 阅读2分钟

要是有人跟你讲,他是富二代,普通青年,穷一代。请相信他,世界那么大,有什么奇怪的呢,不信来看下这个:

let a;
if (a == 1 && a == 2 && a == 3) {
    console.log('没错,这就是我')
}

请问,这个 a 是什么?

这不就是我刚才说的那个,富二代,普通青年,穷一代?

看到 == 仿佛明白了点什么,这是弱等于,大概意思是,你跟我比较,那我得要跟你同一个类型比较才算公平,于是,巴拉巴拉小魔仙变身了。会悄悄地转换类型(隐式转换)。所以说,男人不要跟女人...

那么是 a 到底是个什么东西呢?

如果原始类型的值跟对象比较,对象会转换为原始的值,再进行比较,对象转换成原始类型的值,会先调用 valueOf 方法,如果返回的还是对象,再接着调用 toString 方法。

所以,它就是

let a = {
    i: 1,
    toString: () => a.i++
}
if (a == 1 && a == 2 && a == 3) {
    console.log('没错,这就是我')
}

条条大路通罗马,所以还有一个数组的解法,会让你更楞逼不解,瞧:

var a = [1, 2, 3];
a.join = a.shift;
if (a == 1 && a == 2 && a == 3) {
    console.log('没错,这就是我')
}

what?

array 也属于对象,不信你 [] instanceof Object ,那么 arraytoString 又是怎么用的呢?

对于数组对象,toString 方法返回一个字符串,该字符串由数组中的每一个元素的 toString 返回值经过 join() 方法连接组成的。

所以数组对象不光是偷偷调了 toString 方法,还会由 toString 悄咪咪地调用自己的 join 方法。

所以, join 被改写成 shift 刚好返回数组第一个,数组也删除了第一个 ,偷天换日成功!

最后给大家奉上我得知这个神奇的知识的来源 从 (a==1&&a==2&&a==3) 成立中看javascript的隐式类型转换