参考链接:深入浅出Object.defineProperty
一、语法
Object.defineProperty的作用就是直接在一个对象上定义一个新属性,或者修改一个已经存在的属性
Object.defineProperty(obj, prop, desc)
Object.defineProperties(obj, {
prop1: desc,
prop2: desc
})
- obj 是需要定义属性的当前对象
- prop 为当前需要定义的属性名
- desc 为属性描述符
一般通过为对象的属性赋值的情况下,对象的属性可以修改也可以删除,但是通过Object.defineProperty定义属性,通过描述符的设置可以更加精确的控制对象属性。
JavaScript有三种类型属性
- 命名数据属性:Obj.name = ‘xxx’
- 命名访问器属性:通过
getter
和setter
进行读取和赋值的属性 - 内部属性:例如
[[Prototype]]
二、数据描述符&存取描述符
通过Object.defineProperty()为对象定义属性,有两种形式,且不能混合使用。分别为数据描述符、存取描述符。
数据描述符(value, writable)
数据描述符特有的两个属性: value writable
value就是属性的值,writable表示是否可以修改
let person = {}
Object.defineProperty(person, 'name', {
value: 'zx',
writable: false // 是否可以修改(这里不允许修改)
})
person.name = 'tzq'
console.log(person.name) // zx
存取描述符(set, get)
get
: 一个给属性提供getter的方法,如果没有getter则为undefined。该方法返回值被用作属性值。set
: 一个给属性提供setter的方法,如果没有setter则为undefined。该方法将接受唯一参数,并将该参数的新值分配给该属性。
let person = {}
Object.defineProperties(person, {
_name: {
value: 'zx',
writable: true
},
name: {
get: function() {
console.log('getter被调用了!!')
return this._name
},
set: function(val) {
console.log('setter被调用了!!')
this._name = val
}
}
})
person.name = 'tzq' // getter被调用了!!
console.log(person.name) // setter被调用了!! tzq
注意点: get必须要return;并且必须return一个变量,否则无法改变改属性值,写死没有任何意义。
set方法是在对象该属性被修改时触发,用于修改属性值
公共描述符(configrable, enumerable)
- configrable 描述属性可否删除,以及可否再次配置 ```javascript “use strict” let person = {} Object.defineProperty(person, ‘name’, { value: ‘jack’, configurable: false })
delete person.name // cannot delete property ‘name’ of #