理解不了的__proto__和prototype

介绍

prototype(函数的原型)

  1. 只有函数才有
  2. protoype对象默认有两个属性:constructor 和 proto。
  3. prototype是为其他对象提供共享属性的对象

proto

  1. 所有对象都有,内置属性
  2. 指向构造函数对象的原型对象(prototype)
function Person(name, age) {
    this.name = name;
    this.age = age;
}

var person1 = new Person('tom', 2);

// person1是对象只有__proto__属性
// Person是函数具有__proto__、prototype

person1.__proto__ === Person.prototype; // true (__proto__第2条)
Person.prototype.constructor === Person; //true (prototype第2条)
Person.prototype.__proto__ === Object.prototype; // true (prototype第2条)

Person.prototype.sex = 'male';
console.log(person1.sex) // 'male' (prototype第3条)

常见误区

  1. 所有对象字面量创建的对象__proto__指向Object.prototype
var Person = {
	 name: 'tom',
	age: 12
};
Person.__proto__ === Object.prototype; // true
  1. Function,Object是函数类型
console.log(typeof Object) // function
console.log(typeof Function) // function

console.log(Function.__proto__ === Function.prototype); // true
console.log(Object.__proto__ === Function.prototype); // true

console.log(Function.prototype.__proto__ ===  Object.prototype); // true
  1. Object.create
    定义:Object.create(proto,[propertiesObject])
    proto:新创建对象的原型对象
    propertiesObject:可选。要添加到新对象的可枚举(新添加的属性是其自身的属性,而不是其原型链上的属性)的属性。
var Person = {
    name: 'tom',
    age: 12
}
var person1 = Object.create(Person);
console.log(person1.__proto__ === Person); // true

// Object.create实现原理
Object.createMy = function(obj) {
    function f() {};
    f.prototype = obj;
    return new f();
}
var person2 = Object.createMy(Person);
console.log(person2.__proto__ === Person); // true

// 让我们回忆一下new的操作
function Personfun(name, age) {
    this.name = name;
    this.age = age;
}
personfun1 = new Personfun('tom', 13)
console.log(personfun1.__proto__ === Personfun.prototype); // true
console.log(Personfun.prototype.constructor === Personfun); // true

既然说到了就详细说一下Object.create{null}, Object.create{Object.prototype}, {}吧

var obj1 = {a: '1'};
var obj2 = Object.create(Object.prototype,{
    a:{
           writable:true,
        configurable:true,
        value:'1'
    }
});
var obj3 = Object.create(null);

obj1.toString();
obj2.toString();
obj3.toString(); // TypeError: obj3.toString is not a function

// obj1 和 obj2 是创建方式是一致的,存在Object原型链上的方法
// obj3是一个存粹对象,什么时候使用Object.create(null)呢?
// 		- 你需要一个非常干净且高度可定制的对象当作数据字典的时候;
// 		- 想节省hasOwnProperty带来的一丢丢性能损失并且可以偷懒少些一点代码的时候


图说天下

在这里插入图片描述
原型链:利用原型让一个引用类型继承另一个引用类型的属性和方法
在这里插入图片描述

参考:
https://segmentfault.com/a/1190000016364830
https://juejin.im/entry/6844903790345191437

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值