关于Object.defineProperty()使用

191 阅读2分钟

Javascript提供了一个内部数据结构,用来描述对象的属性,属性的描述对象共有6个属性:

{
    value:undefined,
    writable:true,
    enumerable:true,
    configurable:true,
    set:undefines,
    get:undefined
}
  1. value value是该属性的属性值,默认是undefined

  2. writable writable是一个布尔值,表示value是否可改变,默认是true

  3. enumerable enumerable表示该属性是否可遍历,默认为true

4.configurable

configurable表示该属性是否可配置,默认为true。如果设置为false,该属性其他可配置的描述对象将不能再改变

  1. set set是一个函数,表示该属性的存值函数(setter),默认为undefined

  2. get get是一个函数,表示该属性的取值函数(getter),默认为undefined

在这六个描述属性中是有冲突的情况

1.valueget同时定义
var obj = Object.defineProperty({},'name',{
    value:'张三',
     get(){
         return '李四'
     }
})
console.log(obj.name)
//Uncaught TypeError: Invalid property descriptor. Cannot both specify accessors and a value 
//or writable attribute, #<Object>
2.writableget同时定义
var obj = Object.defineProperty({},'name',{
    writable:true,
    get(){
        return '李四'
    }
})
console.log(obj.p)
//Uncaught TypeError: Invalid property descriptor. Cannot both specify accessors and a value or
//writable attribute, #<Object>
3.configurablewritable

configurable返回布尔值,当configurablefalse时,writableenumerableconfigurable都不能被修改。如果修改会报错。但是当writabletrue改为false时不会报错。

configurable:false

writabletrue改为false

var obj = Object.defineProperty({},'name',{
    writable:true,
    configurable:false
})
Object.defineProperty(obj,'name',{
    writable:false,
    configurable:false
})
console.log(Object.getOwnPropertyDescriptor(obj,'name'))
//{
//    value: undefined, 
//    writable: false, 
//    enumerable: false, 
//    configurable: false
}

configurable:false

writablefalse改为true

var obj = Object.defineProperty({},'name',{
    writable:flase,
    configurable:false
})
Object.defineProperty(obj,'name',{
    writable:true,
    configurable:false
})
console.log(Object.getOwnPropertyDescriptor(obj,'name'))
// Cannot redefine property: name at Function.defineProperty

configurablewritable只要有一个设置为true那么该属性的value值就能够被改变,例:

var obj = Object.defineProperty({},'name',{
    value:'张三',
    writable:true,
    configurable:false
})
obj.name = '李四'
console.log(obj.name)
//李四
var obj = Object.defineProperty({},'name',{
    value:'张三',
    writable:false,
    configurable:true
})
Object.defineProperty(obj,'name',{value:'王五'})
//调用的是配置功能,configurable是true所以是成功的
//王五
obj.name = '王五' 
console.log(obj.name)
//访问的set,但是writable是false,所以不成功
//张三