函数名
- 通过Function.name的方式可以拿到函数名
function test() {}
console.log(test.name); //test
let a = new Function();
console.log(a.name); // anonymous
对象属性名隐式转换
- 定义属性名时,会通过String包装类对属性名进行转换
var obj = {};
var fun = function(){}
obj[obj] = 3; // obj['object Object']
obj[1] = 1; // obj['1']
obj[true] = 2; // obj['true']
obj[fun] = 4; // obj['function (){}']
obj[null] = 9; // obj['null']
obj[undefined] = 9; // obj['undefined']
console.log(obj);
obj = {
'1': 1,
'true': 2,
'[object Object]': 3,
'function(){}': 4
}
Object.getOwnPropertyDescriptor Object.defineProperty
- Object.getOwnPropertyDescriptor 获取对象属性的描述符
- Object.defineProperty 定义对象属性的操作权限
var obj = {};
Object.defineProperty(obj, 'a', {
value: 1, // 属性值
writable: false, // 是否可以重新赋值 此处省略则默认为false
configurable: false, // 是否可以删除 此处省略则默认为false
enumerable: false // 是否可以被遍历 此处省略则默认为false 它决定了浏览器控制台属性颜色的深浅,false则为浅色
})
obj.a = 2; // 此时会静默失败 'use strict' 模式下 error
delete obj.a; // 此时会静默失败 ‘use strict’ 模式下 error
console.log(obj.a); // 1
console.log({...obj}); // { }
Object.assign({}, obj); //{ }
- 通过字面量定义或obj.a添加属性,上面的属性描述均为true.
- 当字面量属性和Object.defineProperty同时存在时,属性权限默认均为true
var obj = {};
obj.a = 1;
Object.defineProperty(obj, 'a', {
value: 2,
writable: false
})
console.log(Object.getOwnPropertyDescriptor(obj, 'a'));
getOwnPropertyDescriptor只能获取自身属性,原型属性无法获取
扩展
- Object.defineProperties 用法
var obj = Object.defineProperties({}, {
a: {
value: 1,
writable: true
},
b: {
value: 1
}
});
console.log(obj); // { a: 1, b: 1 }
- Object.getOwnPropertyDescriptors
var obj = { a: 1, b: 2 }
var des = Object.getOwnPropertyDescriptors(obj);
console.log(des); // output
{
a: {
value: 1,
writable: false,
enumerable: false,
configurable: false,
},
b: {
value: 1,
writable: false,
enumerable: false,
configurable: false,
}
}
getter setter
- 也叫伪属性的使用
- 如何定义:
- 在伪属性前使用 get 或 set 后面要跟伪属性方法
- 根据伪属性对应的方法,输出或设置真正的值
- set必须要有参数,否则 error
- get和set最好配套使用,否则无法通过.语法进行另一种操作
var obj = {
get a(){ ...业务逻辑 },
set a(x){ ...业务逻辑 }
}
obj.a // 相等于调用obj的 get a(){}
obj.a = 1; // 相当于调用obj的 set a(){}
Object.defineProperty(obj, 'c', {
get: () => 1, // 如果涉及到this,最好不用arrow function
set: function (val) { this.a = val }, // 最好不要用箭头函数
writable: false, // error 使用了get不能再使用该属性
value: 1 // error 使用了get不能再使用该属性
configurable: false, // 可正常使用
enumerable: false // 可正常使用
})
get set常规用法
var obj = {
_a: '',
get a(){
return this._a;
},
set a(val){
this._a = val + 1
}
}
Object.create
- Object.create({}) 创建出来的对象的原型指向{},而非原型链顶端。
var a = {};
var b = Object.create(a);
b.__proto__ === a; // true
b.__proto__ === Object.prototype; // false
a.__proto__ === Object.prototype; // true
- Object.create 直接定义对象,可以直接定义对象属性的权限
Object.create(null); // {} 没有原型
Object.create({}, {
a: { // 这里可以直接定义property的descriptor(描述符)
value: 1,
enumerable: true
},
b: {
value: 2
}
})
Object.is
- Object.is() 对两个值进行全等比较。和===不同的是,比较NaN时,不再是false。
两种和===结果不同的情况:
Object.is(NaN, NaN); // true
Object.is(+0, -0); // false
其他情况和===的结果相同
Object.getPrototypeOf
- Object.getPrototypeOf 获取对象的原型
var obj = {}
console.log(Object.getPrototypeOf(obj)); // 等价于 obj.__proto__ Object.prototype
- Object.setPrototypeOf 设置对象原型
var obj = {}
var proto = { x: 1, y: 2 }
var objNew = Object.setPrototypeOf(obj, proto);
console.log(Object.getPrototypeOf(obj) === proto ); // true
console.log(Object.getPrototypeOf(objNew) === proto ); // true
第一个参数为目标对象。第二个参数为对象的原型。
var num = 1;
Object.setPrototypeOf(num, {x: 1}); //静默失败 相当于new Number(num).__proto__ = {x: 1}
Object.getPrototypeOf(num).x; // undefined 相当于new Number(num).__proto__.x
类比分析见下:
var num = 1;
Number.prototype.x = 2;
num.x; // 2
原始值没有自己的属性。那它为何可以通过num.x拿到2。
原因:num.x底层做了包装类转换,是通过new Number(num)取到构造函数Number的prototype 。
num.x = 3;// 静默失败
既然没有属性,自然不能设置属性赋值,具体的原理如下:
包装类转换:new Number(num).x = 3 ,但没有变量承接new Number(num),于是会对其销毁,所以无法设置x。
Object.entries
- 获取对象的key value的集合,集合为数组形式
- 无法获取继成属性及不可枚举属性。但for in 可以获取到继承属性。
var obj = {
x: 1,
y: 2,
a: 3
}
Object.entries(obj);
// 形式如下:
[
[ 'x', 1 ],
[ 'y', 2 ],
[ 'a', 3 ]
]
Object.keys(obj); // [ 'x', 'y', 'a' ]
Object.values(obj); // [ '1', '2', '3' ]
extend
- 涉及到系统自动遍历值对象属性时,通常字符串都会转成String对象,String对象是类数组可以被遍历。
Object.keys('123'); // [ '0', '1', '2' ]
还有:
Object.assign([1, 2, 3, 4], '123'); // [ '1', '2', '3', 4 ]
[1, 2, 3, ...'123']; // [1, 2, 3, '1', '2', '3']
for in
等
English word
anonymous [əˈnɑːnɪməs] 匿名的 e 拿呢 摩斯
configurable [kənˈfɪgjərəbl] ken fei gei wo bo 可配置
enumerable i miu 弱2 bo 可枚举的
enum ai ne mu