JS Object.getOwnPropertyDescriptor()和Object.defineProperty()

本文详细解析了ECMAScript5中对象属性的特性,通过使用Object.getOwnPropertyDescriptor()和Object.defineProperty()方法,展示了如何获取和修改属性的可写、可枚举、可配置等特性,并提供了实例演示。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

ECMAScript 5 对对象属性进行了重新定义。除了原有的 property:value外,还增加了一些用于 标识该属性是否可写,可枚举,可配置的特性。为此引入了两个新方法:Object.getOwnPropertyDescriptor()和Object.defineProperty()。

<script>
var person ={ name:"Hai" }; //定义一个新对象
var personName = Object.getOwnPropertyDescriptor(person,"name"); //获取name属性身上的特性
console.log(personName);  //输出为{value: "Hai", writable: true, enumerable: true, configurable: true}
var personToString = Object.getOwnPropertyDescriptor(person,"toString"); //注意这里的Own,它的意思是只能获取对象本身自有的属性的特性
console.log(personToString); //因为toString()是Object的方法,是继承来的,所以返回undefined
Object.defineProperty(person,"name",{writable:false}); //修改name属性的可写特性为false,则不可以对name重新赋值
personName = Object.getOwnPropertyDescriptor(person,"name"); //再次获取name属性的特性
console.log(personName); //{value: "Hai", writable: false, enumerable: true, configurable: true}
person.name = "dingding"; //强行修改name
console.log(person.name); //这里仍然输出 “Hai”
</script>

 

转载于:https://www.cnblogs.com/princeding/p/4436618.html

<think>好的,我现在需要解决用户的问题:如何通过Object.getOwnPropertyDescriptor结合Object.defineProperty动态更新属性描述符的值。首先,我需要回顾这两个方法的作用用法。 用户提到了Object.defineProperty,这个方法用于定义或修改对象的属性描述符。而Object.getOwnPropertyDescriptor则是用来获取对象某个属性的描述符。动态更新可能需要先获取当前的描述符,然后修改其中的某些特性,再重新应用回去。 接下来,我需要确保步骤正确。首先,使用Object.getOwnPropertyDescriptor获取当前描述符,这可能包括value、writable、enumerable、configurable等属性。然后,检查这个描述符是否存在,如果属性不存在,返回undefined。接着,修改需要变更的部分,比如value或者writable的值。最后,使用Object.defineProperty将修改后的描述符应用到对象上。 需要注意的是,如果原属性的configurable为false,那么无法重新配置该属性,会抛出错误。所以必须确保属性是可配置的。例如,如果原属性的writable为false,且没有设置configurable为true,那么不能修改value,除非writable被改为true。这可能是一个容易出错的地方,需要提醒用户注意。 另外,用户可能希望动态更新属性,比如根据条件改变getter或setter函数,或者调整enumerable的值。这时候,获取描述符后,替换对应的函数或值,再重新定义即可。例如,修改getter函数后,再次调用Object.defineProperty应用新的描述符。 我应该举例说明,比如先创建一个对象obj,有一个属性a,然后获取其描述符,修改value或writable,再重新定义。同时,处理访问器属性的情况,比如修改getter。另外,需要强调configurable的重要性,如果不可配置,则无法修改。 可能还需要提到错误处理,比如在尝试修改不可配置属性时捕获TypeError。这样用户在实际应用中能避免程序崩溃。 最后,总结步骤:获取描述符、修改描述符属性、重新定义属性。同时,注意事项包括configurable的设置潜在的错误处理。确保示例代码覆盖数据属性访问器属性两种情况,以全面展示方法的应用。</think>### 通过 `Object.defineProperty` 结合 `Object.getOwnPropertyDescriptor` 动态更新属性描述符的值 #### 步骤说明 1. **获取属性描述符** 使用 `Object.getOwnPropertyDescriptor(obj, prop)` 获取目标属性的描述符对象,包含 `value`、`writable`、`enumerable`、`configurable` 等特性[^2][^3]。 2. **修改描述符属性** 直接修改获取到的描述符对象中的特性值(例如 `value`、`writable`),或替换 `get`/`set` 方法(若为访问器属性)。 3. **重新定义属性** 通过 `Object.defineProperty(obj, prop, modifiedDescriptor)` 将修改后的描述符应用到对象属性上[^4]。 #### 代码示例 ```javascript // 示例对象 const obj = {}; // 初始定义属性 Object.defineProperty(obj, 'a', { value: 1, writable: false, enumerable: true, configurable: true // 必须为 true 才能修改描述符 }); // 1. 获取属性描述符 const descriptor = Object.getOwnPropertyDescriptor(obj, 'a'); console.log(descriptor.value); // 输出: 1 // 2. 修改描述符属性 descriptor.value = 2; descriptor.writable = true; // 3. 重新定义属性 Object.defineProperty(obj, 'a', descriptor); // 验证修改结果 console.log(obj.a); // 输出: 2 obj.a = 3; console.log(obj.a); // 输出: 3 (writable 已生效) ``` #### 动态更新访问器属性 ```javascript const obj2 = {}; // 初始定义访问器属性 let internalValue = 10; Object.defineProperty(obj2, 'b', { get() { return internalValue; }, set(newVal) { internalValue = newVal; }, configurable: true }); // 获取并修改描述符 const descriptor2 = Object.getOwnPropertyDescriptor(obj2, 'b'); descriptor2.get = function() { return internalValue * 2; }; // 修改 getter // 重新定义属性 Object.defineProperty(obj2, 'b', descriptor2); console.log(obj2.b); // 输出: 20 (原值为10,修改后返回双倍) ``` #### 注意事项 1. **`configurable` 必须为 `true`** 若原属性的 `configurable` 为 `false`,则无法修改除 `writable` 以外的特性,且 `writable` 只能从 `true` 改为 `false`[^5]。 2. **错误处理** 若尝试修改不可配置属性,会抛出 `TypeError`,建议用 `try...catch` 包裹代码。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值