浅谈Object.defineProperty()

前言

        Object.defineProperty()是直接在一个对象上定义一个新的属性,或者是修改已存在的属性。最终这个方法会返回该对象。简单来说就是为对象定义属性。那么在我们使用 Object.defineProperty()之前,我们是如何给对象添加或者修改属性的,下面看代码

var obj = {}
obj.name = '张三'
obj['age'] = 18
console.log(obj)    // {name: "张三", age: 18}

我们可以很简单的就为对象添加或者修改一个属性,那为啥还需要Object.defineProperty()呢?那是因为Object.defineProperty()可以更深层次的定义属性,下面详细介绍。

参数

Object.defineProperty(obj, prop, descriptor)

obj:必须:要在其上添加或修改属性的对象
prop:必须:一个包含属性名称的字符串
descriptor 必需。 属性描述符。 包含6个属性:configurable、enumerable、writable、value、get、set

obj和prop很好理解,我们详细说一下descriptor参数吧:

configurable

configurable如果为false,那么除了value和writable之外的特性都不能被修改(包括自身),并且writable为true可修改为false,如果writable为false,修改为true也会被忽略

var obj = {
    name: '张三',
}
Object.defineProperty(obj,'name',{
    configurable: false
})
console.log(obj)    // {name: "张三"}

// 修改value值
Object.defineProperty(obj,'name',{
    value: '李四',
})
console.log(obj)    // {name: "李四"}

// 修改writable为false
Object.defineProperty(obj,'name',{
    writable: false
})
obj.name = '王五'
console.log(obj)    // {name: "李四"}

enumerable

enumerable为true代表可枚举,为false为不可枚举,默认值是true。for in可以遍历出可枚举的属性。

var obj = {
    name:'张三'
}
// 把age的enumerable属性设为false代表不可枚举,这个时候for in是遍历不出来这个属性的
Object.defineProperty(obj,'age',{
    value: 18,
    enumerable: false
})
for (const key in obj) {
    console.log(key)    // name
}

// enumerable为true的情况
Object.defineProperty(obj,'address',{
    value: '上海',
    enumerable: true
})
for (const key in obj) {
    console.log(key)    // name,address
}

writable

writable为true的时候可以改变属性的value值,如果writable为false的时候修改value值无效

var obj = {
    name:'张三'
}
// 把age的enumerable属性设为false代表不可枚举,这个时候for in是遍历不出来这个属性的
Object.defineProperty(obj,'age',{
    value: 18,
    writable: true
})
obj.age = 99
console.log(obj)    // {name: "张三", age: 99}

// 将writable设置为false
Object.defineProperty(obj,'age',{
    writable: false
})
obj.age = 100
console.log(obj)    // {name: "张三", age: 99}     这个时候修改age会失效

value

value就是某个属性的值

var obj = {}
// value代表将name的属性值设置为赵六
Object.defineProperty(obj,'name',{
    value: '赵六'
})
console.log(obj)    // {name: "赵六"}

get

在读取属性时调用的函数。默认值是undefined

var obj = {}
Object.defineProperty(obj, 'name', {
    get: function() {
        return '张三'
    }
})
console.log(obj.name)   // 张三

set

在写入属性时调用的函数。默认是undefined

var obj = {}
var name = '张三'
Object.defineProperty(obj, 'name', {
    get: function () {
        return name
    },
    set: function(newVal) {
        (name !== newVal) && (name = newVal)
    }
})
console.log(obj.name)   // 张三
obj.name = '李四'
console.log(obj.name)   // 李四
console.log(name)       // 李四

// 啊这,不就是双向数据绑定的原理吗

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值