原型和原型链
概念
- 隐式原型:
__proto__ - 显式原型:
prototype
特性
- 对象
__proto__的值等于其构造函数的prototype
js
const obj = {};
const arr = [];
const fn = function () {};
obj.__proto__ == Object.prototype; // true
arr.__proto__ === Array.prototype; // true
fn.__proto__ == Function.prototype; // true- 在访问对象的某个属性时,如果这个对象本身没有,那么它会去它的
__proto__(构造函数的显式原型prototype)中寻找
js
const obj = { a: 1 };
obj.toString;
// ƒ toString() { [native code] }练习
js
function Fn() {}
const fn = new Fn();
console.log('fn.prototype', fn.prototype);
console.log('fn.__proto__', fn.__proto__);
console.log('fn.__proto__ === Fn.prototype', fn.__proto__ === Fn.prototype);
console.log('Fn.__proto__', Fn.__proto__);
console.log('Fn.prototype', Fn.prototype);
console.log('Fn.prototype.__proto__', Fn.prototype.__proto__);
console.log(
'Fn.prototype.__proto__ === Object.prototype',
Fn.prototype.__proto__ === Object.prototype
);
console.log('fn.constructor === Fn', fn.constructor === Fn);
console.log('Fn.constructor', Fn.constructor);
说明
- 在你的情况下,
Fn.__proto__的输出是ƒ () { [native code] },这表示Fn的原型是由 JavaScript 引擎内部实现的,而不是通过常规的 JavaScript 代码创建的。这是因为函数的原型通常由引擎实现,而不是由开发人员手动定义。
参考
补充
说出以下打印,为什么
js
function Fn(){}
console.log(Function.prototype === Object.__proto__)
console.log(Fn.__proto__ === Object.__proto__)
console.log(Fn.__proto__ === Function.__proto__)
console.log(Object.__proto__ === Function.__proto__)- 简单记忆,所有函数最终都收敛到
Function.prototype,所有对象都收敛到Object.prototype,或者说null - 在 JavaScript 中,
Fn.__proto__和Function.__proto__都指向Function.prototype,而Function.prototype是一个原生函数的引用,因此打印它们时会显示ƒ () { [native code] }。由于它们指向同一个对象,所以比较它们是否相等时会返回true。