JavaScript中,类型转换实在是太常见了。分为显示类型转换和隐式类型转换。
今天讨论的不是什么情况下,发生类型转换,而是在特定条件下,对象是怎么发生类型转换的。
以显示类型转换的方法Number()为例:
关于Number()的转换方法在《JavaScript高级程序设计》有详细的介绍
我们现在关注的焦点在红线框出来的这块。
var obj = {
toString: function() {
return "456"
},
valueOf: function() {
return 123;
}
}
console.log(Number(obj))
在浏览器当中验证一下,返回123,如果按照我们对红线框出来的这句话理解,那么如果我们在重写valueOf的方法时,让其返回值变成NaN,那么他是不是就会再次调用toString方法呢?
var obj = {
toString: function() {
return "456"
},
valueOf: function() {
return NaN;
}
}
console.log(Number(obj))
在浏览器中查看答案:
很抱歉,依然是NaN,并没有调用toString方法,什么情况这是?
很纠结吧!
稍作变形:
var obj = {
toString: function() {
return "456"
},
valueOf: function() {
return {
result: 124
};
}
}
console.log(Number(obj))
当valueOf返回一个对象时,此时Number(obj)的返回结果居然是数字456,是不是很惊喜?仔细琢磨一下,发现:
在使用Number()对对象做显示类型转换时,优先调用valueOf方法,当返回结果非基本类型值时,他会再次调用toString方法。注意:如果这两个方法都重写了,而且返回值都是非基本类型值的话,会报错。
var obj = {
toString: function() {
return {
num: 12
}
},
valueOf: function() {
return {
result: 124
};
}
}
console.log(Number(obj))
报错如下:
而如果仅仅重写了其中一个方法,无论哪个,他都优先调用重写后的方法,返回基本类型值之后,再按照基本类型值进行类型转换,转换为数值。
关注点在:重写了两个方法之后,如果valueOf直接返回NaN,并不会再次调用toString。