9. Object API
- 关于对象,引入了哪些新的语法糖?
解构
解构可以简化获取对象属性。// const prop = obj.prop;
const { prop } = obj;
在解构时,可以重命名属性:
解构可以写在函数参数里:
数组可以使用特殊的方括号进行解构:属性简写
在对象字面量中,可以简写属性/值对。 ```javascript const prop = ‘prop’; const method = function () {};
/ const obj = { prop: prop, method: method, } /
const obj = { prop, method, };
- getter/setter<br />以前使用 `Object.definedProperty()`,现在可以直接在对象字面量中定义 getter/setter,
```javascript
/* const obj = {};
Object.defineProperty(obj, 'prop', {
get: function (){},
set: function (value) {},
}); */
const obj = {
get prop() {},
set prop(value) {},
};
- 计算属性
可以在对象字面量中使用方括号来定义计算属性。 ```javascript let i = 0;
const obj = {
};
console.log(obj[0]); // -> ‘value’
- 扩展操作符<br />使用扩展运算符可以便捷地拷用其他对象。
```javascript
const user = {
name: 'trigold',
id: Math.random().toString(36),
};
const newUser = {
updatedAt: new Date().toLocaleString(),
...user,
};
console.log(newUser);
/* {
updatedAt: '2022/5/29 14:36:48',
name: 'trigold',
id: '0.ye9ml0rfifs'
} */
- 对象属性有哪几种?有几种获取对象属性名的方法?
for-in
枚举在使用for-in循环时,返回的是所有能够通过对象访问的、可枚举的属性,其中既包括存在于实例中的属性,也包括存在于原型中的属性,屏蔽了原型中不可枚举属性的实例属性也会在for-in循环中返回。
Object.keys()
获取的是对象实例本身的可枚举属性,不包括原型中的属性。
Object.getOwnPropertyNames()
获取的是对象本身的所有属性(不包括原型的属性),既包括可枚举属性,也包括不可枚举属性。
- 属性的特性有哪些?怎么访问这些特性?
[[Configurable]]
表示属性是否可以通过delete
删除并重新定义,是否可以修改它的特性,以及是否可以把它改为访问器属性,默认属性下,所有直接定义在对象上的属性的这个特性都是true
.[[Enumerable]]
表示属性是否可以通过for-in
循环返回.默认情况下,所有直接定义在对象的属性的这个特性都是true
[[Writable]]
表示属性的值是否可以被修改,默认情况下,所有直接定义在对象上的属性的这个特性都是true
[[Value]]
包含属性实际的值.这就是前面提到的那个读取和写入属性值的位置,这个特性的默认值是undefined
- Object.freeze 有什么作用?与它类似的方法有哪些?手写一个“深冻结”。
**Object.freeze()**
方法可以冻结一个对象。一个被冻结的对象再也不能被修改;冻结了一个对象则不能向这个对象添加新的属性,不能删除已有属性,不能修改该对象已有属性的可枚举性、可配置性、可写性,以及不能修改已有属性的值。此外,冻结一个对象后该对象的原型也不能被修改。freeze()
返回和传入的参数相同的对象。
使用 const 声明的对象值,它的值是可以改变的,怎么可以使得对象的值不可改变?
- Object.freeze
- Object.seal
**Object.seal()**
方法封闭一个对象,阻止添加新属性并将所有现有属性标记为不可配置。当前属性的值只要原来是可写的就可以改变。可以被修改
- Object.preventExtensions
**Object.preventExtensions()**
方法让一个对象变的不可扩展,也就是永远不能再添加新的属性。
- 深/浅冻结
Object.freeze 是“浅冻结”,如下面的代码所示:
const obj1 = {
info: 'obj1',
};
const obj2 = Object.freeze({
info: 'obj2',
obj1,
});
log(obj2);
obj2.obj1.info = 'obj2 changed';
log(obj2);
- 实现深冻结
'use strict';
const { log } = console;
Object.deepFreeze = function deepFreeze(obj) {
let propNames = Object.getOwnPropertyNames(obj);
propNames.forEach((name) => {
let prop = obj[name];
if(typeof prop === 'object' && prop !== null) {
Object.deepFreeze(prop);
}
});
return Object.freeze(obj);
};
const obj1 = {
info: 'obj1',
};
const obj2 = Object.deepFreeze({
info: 'obj2',
obj1,
});
log(obj2);
obj2.obj1.info = 'obj1 changed';
log(obj2);