高程阅读笔记——对象

遍历对象的几种方法

for in 
Object.keys      [返回键]
Object.values    [返回值]
Object.entries    [返回键值对]

for in

会遍历自身以及原型链上所有可枚举属性

Object.keys

遍历自身可枚举属性

Object.getOwnPropertyNames()

自身所有属性

String 类型也有concat属性

Object.setPrototype Object.getPrototype

设置获取原型链【—proto—】

1. Object.getPrototype

Object.getPrototypeOf方法返回一个对象的原型。这是获取原型对象的标准方法。

// 空对象的原型是Object.prototype
Object.getPrototypeOf({}) === Object.prototype
// true

// 函数的原型是Function.prototype
function f() {}
Object.getPrototypeOf(f) === Function.prototype
// true

// f 为 F 的实例对象,则 f 的原型是 F.prototype
var f = new F();
Object.getPrototypeOf(f) === F.prototype
// true

2. Object.setPrototypeOf()

Object.setPrototypeOf方法可以为现有对象设置原型,返回一个新对象。

Object.setPrototypeOf方法接受两个参数,第一个是现有对象,第二个是原型对象。

var a = {x: 1};
var b = Object.setPrototypeOf({}, a);
// 等同于
// var b = {__proto__: a};

b.x // 1
  • new命令通过构造函数新建实例对象,实质就是将实例对象的原型,指向构造函数的prototype属性,然后在实例对象上执行构造函数。

1.对象实现iterator

Object.defineProperty(Object.prototype,Symbol.iterator,{
    value: function* f() {
        let keys = Object.keys(this);
        for(let i = 0;i

2. iterator原始写法

# -原生实现generator 函数

Object.defineProperty(Object.prototype, Symbol.iterator,{
    value: function () {
        let keys = Object.keys(this)
        let that = this
        let couter = 0
        return  {
                next(){
                    couter++
                    return{
                        value: that[keys[couter-1]],
                        done: couter > keys.length
                    }
                }
        }
    }
})

// var c = { a: 1, b: 2 }
// let iterator = c[Symbol.iterator]()
// iterator.next()

var c = { a: 1, b: 2 }
for (let i of c) {
    console.log(i)
}

需要掌握 API Object.creat Oject.defineProperty

  • Object.creat

生成实例对象的常用方法,就是使用new命令,让构造函数返回一个实例。但是很多时候,只能拿到一个实例对象,它可能根本不是由构建函数生成的,那么能不能从一个实例对象,生成另一个实例对象呢?

JavaScript 提供了Object.create方法,用来满足这种需求。该方法接受一个对象作为参数,然后以它为原型,返回一个实例对象。该实例完全继承原型对象的属性。

// 原型对象
var A = {
  print: function () {
    console.log('hello');
  }
};

// 实例对象
var B = Object.create(A);
B.print() // hello
B.print === A.print // true

除了对象的原型,Object.create方法还可以接受第二个参数。该参数是一个属性描述对象,它所描述的对象属性,会添加到实例对象,作为该对象自身的属性。

var obj = Object.create({}, {
  p1: {
    value: 123,
    enumerable: true,
    configurable: true,
    writable: true,
  },
  p2: {
    value: 'abc',
    enumerable: true,
    configurable: true,
    writable: true,
  }
});

// 等同于
var obj = Object.create({});
obj.p1 = 123;
obj.p2 = 'abc';

Object.create方法生成的对象,继承了它的原型对象的构造函数。

继承的时候别忘了写constructor

function A() {}
var a = new A();
var b = Object.create(a);

b.constructor === A // true
b instanceof A // true
  • Object.prototype.isPrototypeOf()

对象实例的isPrototypeOf方法,用来判断一个对象是否是另一个对象的原型。

var o1 = {};
var o2 = Object.create(o1);
var o3 = Object.create(o2);

o2.isPrototypeOf(o3) // true
o1.isPrototypeOf(o3) // true

上面代码表明,只要某个对象处在原型链上,isPrototypeOf都返回true。

Object.prototype.isPrototypeOf({}) // true
Object.prototype.isPrototypeOf([]) // true
Object.prototype.isPrototypeOf(/xyz/) // true
Object.prototype.isPrototypeOf(Object.create(null)) // false

上面代码中,由于Object.prototype处于原型链的最顶端,所以对各种实例都返回true,只有继承null的对象除外。

proto

根据语言标准,proto属性只有浏览器才需要部署,其他环境可以没有这个属性,而且前后的两根下划线,表示它本质是一个内部属性,不应该对使用者暴露。因此,应该尽量少用这个属性,而是用Object.getPrototypeof()(读取)和Object.setPrototypeOf()(设置),进行原型对象的读写操作。

原型链可以用proto很直观地表示。

  • 获取实例对象obj的原型对象,有三种方法。
obj.__proto__
obj.constructor.prototype
Object.getPrototypeOf(obj)

你可能感兴趣的:(高程阅读笔记——对象)