JavaScript原型之对象属性设置与屏蔽

我的最新博客地址:我的最新博客

前言

JavaScript和面向类的语言不同,在ES6出现之前,它其实并没有类来作为对象的抽象模式,所以在描述对象中不免会遇到一个特别的词语,没错就是原型prototype,今天我们讨论的主角也是它,今天我们就来讨论JavaScript原型中的冰山一角。

三道面试题

让我们先来看三道面试题,慢慢的打开你的视野:
先列出三道题目都会用到的对象objProto:

const objProto = {
    
    }
// 题目一
objProto.a = 23
const obj = Object.create(objProto)
obj.a = 24
console.log(obj.a)
console.log(obj.hasOwnProperty('a'))
// 题目二
// 设置objProto对象的a属性为只读属性
Object.defineProperty(objProto, 'a', {
    
    
	enumerable: true,
  	configurable: true,
	value: 23,
	writeable: false
})
const obj = Object.create(objProto)
obj.a = 24
console.log(obj.a)
console.log(obj.hasOwnProperty('a'))
// 题目三
Object.defineProperty(objProto, 'a', {
    
    
	enumerable: true,
  	configurable: true,
	get() {
    
    
		return 23
	},
	set() {
    
    
		console.log('对象objProto的a属性被设置了!')
	}
})
const obj = Object.create(objProto)
obj.a = 24
console.log(obj.a)
console.log(obj.hasOwnProperty('a'))

那么你知道上述三道题的答案吗?
让我们来一一进行分析吧:

题目一

对于第一道题,这是我们大多数人都知道并且了解的场景,答案也很明显,没错就是控制台会打印24和true,那么我们再来看看题目一中的对象obj长啥样,如下图:

在这里插入图片描述
通过上图我们不难看出,对象a被加在了obj对象的自身属性上了,其原型上的属性a还是原来的23,有没有人会以为改变的是原型上的a属性的值呢?我想还是会有人这样认为的吧。那么为什么a属性被加在obj自身上而不是改变其原型上的a属性呢,obj对象自身原本是不存在a的啊。原因我们待会儿再来解释,我们不妨先来看后面两道题目。

题目二

对于题目二,你的答案又是什么呢?
好吧,先让我来告诉你答案吧,控制台会打印出23和false,哈哈,是不是出乎你的意料呢?那我们再来看看obj对象长啥样吧,如下图:

在这里插入图片描述
what fuck?obj对象里面空空如也,为什么,我明明对obj对象的a属性进行赋值操作了啊 obj.a = 24 ,既然都进行赋值操作了,那为什么obj对象还空空如也呢,先保留着你的疑问,让我们先来看第三道题目。

题目三

题目三的答案你想到了吗?好了,不卖关子了,直接说了,题目三的控制台会打印23和false,同上我们先来看看obj对象长啥样,如下图:

在这里插入图片描述
what fuck?obj.hasOwnProperty(‘a’)不是false吗?为什么控制台打印obj对象,还能看到其自身属性也有a属性?what fuck?这到底是怎么一回事呢?

总结

我们先来总结一下:
对于对象自身不含有的属性而其原型对象含有的属性,当我们设置此属性时的几种情况:

  1. 如果原型对象objProto的此属性并没有被标记为只读属性,那么会直接在obj对象自身属性上创建该属性为一个新属性,这就是屏蔽属性
  2. 如果原型对象objProto的此属性被标记为只读属性,那么无法修改原型的此属性值也无法在对象obj自身上创建该属性,也就是此情况下不会发生屏蔽属性。如果是严格模式下, obj.a = 24 这行代码会报错,否则赋值语句 obj.a = 24 会被忽略,总之不会发生屏蔽。
  3. 如果原型对象objProto的此属性,并且有setter,那就一定会调用这个setter。根据 obj.hasOwnProperty(‘a’) 的值为false,我们可以得知该属性并不会被添加到obj自身上(可是我们在控制台打印obj又会看到obj自身属性中含有a,对于三,笔者我也没想明白咋回事,明明hasOwnProperty为false,但是又看到了其自身属性确实有a属性的存在,语言bug?)

第一种情况是我们日常开发中遇到的大多数情况,二和三很少遇到,尤其是三,着实让人摸不着头脑,也难怪有很多大神说JavaScript是一门像屎一样的语言,无可厚非,毕竟JavaScript是在短短十天内就被创造出来的,就像我们日常开发一样,时间短速度快那代码自然bug就多呗。虽然JavaScript在某些方面很垃圾,但是其足够的灵活性也让人爱不释手。

好了,今天就聊到这里,有谁知道三是怎么回事的,欢迎给笔者留言。

猜你喜欢

转载自blog.csdn.net/weixin_40920953/article/details/122054592