(1)问题
if(a == 1 && a == 2 && a == 3){
console.log('ok');
}
(2)解答
原理
js 是单线程的,说明这个判断其实是在“不同的时期”运行。
在不同的时期,人可以从小孩成长为大人,再成为老人。
同理,只要让 a 在不同的时期变成不同的值即可。
toString
变量在打印的时候都会调用toString
这个方法,js中所有的数据他的原型链顶端都是对象,我们重写他的toString
方法就好。
var a = {
_a: 0,
toString: () => {
return ++a._a;
}
}
测试代码
var a = {
_a: 0,
toString: () => {
return ++a._a;
}
}
if(a == 1 && a == 2 && a == 3){
console.log('ok');
}
// ok
(3)思考
直接a = true不行吗
不行,忽略了隐式转换的优先级,等号左边是布偶,右边是数字,会把Boolean转为Number,在进行比较。就变成了都是1==1 && 1==2 && 1==3
自然false
(4)扩展
遇上三等号 a===1&&a===2&&a===3
三等号先判断类型,这时候用Object
的数据拦截就行,这个函数的意思的定义指定对象中的属性,是一个很强大的自定义功能。
Object.defineProperties(window, {
_a: {
value: 0,
writable: true
},
a: {
get: function() {
return ++_a
}
}
})
Object.defineProperties
是 JavaScript 中一个用于定义对象属性的方法,它允许你精细控制对象属性的行为,包括读写、枚举、配置和使用特定的 getter 和 setter 函数。语法如下:
Object.defineProperties(obj, props)
其中:
obj
:需要被定义属性的对象。props
:一个或多个属性描述符对象的集合。每个属性描述符包含以下属性:
configurable
:是否可以使用delete
关键字删除该属性,以及是否可以通过属性描述符修改该属性的描述符。默认值为false
。enumerable
:是否可以在for...in
循环中枚举该属性。默认值为false
。value
:属性的默认值。可以是任意的 JavaScript 值。writable
:是否可以修改该属性的值。默认为false
。get
:属性的 getter 函数,当有人尝试访问该属性时,将调用此函数并返回结果。默认值为undefined
。set
:属性的 setter 函数,当有人尝试设置该属性的值时,将调用此函数并进行操作。默认值为undefined
。例如,下面的代码演示了如何使用
Object.defineProperties
定义一个只读的x
属性和可读可写的y
属性:
const obj = {} Object.defineProperties(obj, { 'x': { value: 100, writable: false }, 'y': { value: 200, writable: true } }) console.log(obj.x) // 100 obj.x = 200 // 报错,因为 x 属性是只读的 console.log(obj.y) // 200 obj.y = 300 console.log(obj.y) // 300
总之,
Object.defineProperties
方法是 JavaScript 中定义对象属性的一种强大方式,可以让你极大地控制属性的行为,并可以实现一些高级的特性,如 getter 和 setter 函数。
结束~ 参考文章