原型与原型链

原型 & 原型链

  • 所有对象都是通过new 函数创建
  • 所有的函数也是对象
    • 函数可以有属性和方法
  • 所有对象都是引用类型

原型 prototype

原型: 任何一个JS对象创建时会关联的一个对象 任何根据原型的构造函数创建出来的对象,都会继承原型上的属性

  • 所有函数都有一个prototype属性
  • 默认情况下,prototype属性是一个普通的Object对象
  • 默认情况下,prototype对象有一个属性constructor,它也是一个对象,指向构造函数本身

隐式原型__proto__

  • 所有的对象都有一个__proto__属性,称为隐式原型
  • 默认情况下,隐式原型指向创建该对象的函数的原型
javascript 复制代码
function test() {}
var obj = new test();
obj.__proto__ === test.prototype // true
javascript 复制代码
function create() {
    if (Math.random() < 0.5) {
        return {}
    } else {
        return []
    }
}
var obj = create();
// 得到创建obj的构造函数名称
console.log(obj.__proto__.constructor.name)

当访问一个对象的成员时:

  1. 看该对象自身是否有该成员,如果有直接使用
  2. 在原型链中依次查找是否有该成员,如果有直接使用

原型链

原型链: 原型链是一个对象到另一个对象的链接,它是由__proto__属性连接起来的一系列对象,直到到达null(即对象查找属性的过程) 特殊点:

  1. Function的__proto__指向自身的prototype
  2. Object的prototype__proto__指向null

图解原型链

面试题

javascript 复制代码
// 面试题一
var F = function() {};
Object.prototype.a = function () {}
Function.prototype.b = function () {}
var f = new F();

console.log(f.a, f.b, F,a, F.b)
// function () {} undefined function() {} function() {}
javascript 复制代码
// 面试题二
function A() {}
function B(a) {
    this.a = a;
}
function C(a) {
    if (a) {
        this.a = a;
    }
}
A.prototype.a = 1;
B.prototype.a = 1;
C.prototype.a = 1;

console.log(new A().a) // 1
console.log(new B().a) // undefined
console.log(new C(2).a) // 2
javascript 复制代码
// 面试题三
function User() {}
User.prototype.sayHello = function() {}

var u1 = new User();
var u2 = new User();

console.log(u1.sayHello === u2.sayHello); //true
console.log(User.prototype.constructor); //User Function
console.log(User.prototype === Function.prototype); // false
console.log(User.__proto__ === Function.prototype); // true
console.log(User.__proto__ === Function.__proto__); // true
console.log(u1.__proto__ === u2.__proto__);  // true
console.log(u1.__proto__ === User.__proto__); // false
console.log(Function.__proto__ === Object.__proto__); // true
console.log(Function.prototype.__proto__ === Object.prototype.__proto__); // false
console.log(Function.prototype.__proto__ === Object.prototype); // true

原型链的应用

基础方法

Object.getPrototypeOf(对象) 获取对象的原型 Object.prototype.isPrototypeOf(对象) 判断当前对象(this)是否在指定对象的原型链上 对象 instanceof 函数 判断函数的原型是否在对象的原型链上 Object.create(原型对象,属性对象) 创建一个对象,其隐式原型指向指定的对象 Object.prototype.hasOwnProperty(属性名) 判断一个对象自身是否拥有某个属性

应用

类数组转换为真数组

javascript 复制代码
Array.prototype.slice.call(arguments); // arguments为类数组

实现继承 默认情况下,所有构造函数的父类都是Object

javascript 复制代码
// 实现继承
function inhreit(Son, Father) {
  // 第一种方案
  // Son.prototype = Father.prototype; // 容易造成原型链污染
  // 第二种方案
  // Son.prototype = Object.create(Father.prototype); // 创建一个对象,其隐式原型指向父类的原型对象prototype
  // 第三种方案
  var F = function () {
  };
  F.prototype = Father.prototype;
  Son.prototype = new F();
  Son.prototype.constructor = Son; // 修正构造函数指向
  // Son.prototype.uper = Father; // 增加父类引用
  Son.prototype.uper = Father.prototype; // 增加父类原型对象引用
}

function User(firstName, lastName, age) {
  this.firstName = firstName;
  this.lastName = lastName;
  this.age = age;
  this.fullName = firstName + " " + lastName;
}

User.prototype.sayHello = function () {
  console.log(`大家好,我是${this.fullName},今年${this.age}岁了!`)
}

function VipUser(firstName, lastName, age, money) {
  User.call(this, firstName, lastName, age)
  this.money = money;
}

inhreit(VipUser, User)
VipUser.prototype.upgrade = function () {
  console.log(`使用${this.money}元,升级VIP会员!`)
}
const vUser = new VipUser('Tom', 'Hanks', 25, 10000)
相关推荐
咪库咪库咪5 分钟前
js的浅拷贝与深拷贝
javascript
幸福的猪在江湖6 分钟前
第一章:变量筑基 - 内力根基修炼法
javascript
Ryan今天学习了吗6 分钟前
💥不说废话,带你使用原生 JS + HTML 实现超丝滑拖拽排序效果
javascript·html
Momoly088 分钟前
vue3+el-table 利用插槽自定义数据样式
前端·javascript·vue.js
多啦C梦a8 分钟前
从 React 初体验到数据驱动的界面开发:一步步解析 Todo List 组件
javascript·react.js
Spider_Man9 分钟前
“AI查用户”也能这么简单?手把手带你用Node.js+前端玩转DeepSeek!
javascript·人工智能·node.js
bo5210010 分钟前
从0到1:Element Plus虚拟树的拖拽功能二次开发实战
javascript·vue.js
小约翰仓鼠10 分钟前
vue3表格使用Switch 开关
前端·javascript·vue.js
满分观察网友z11 分钟前
encodeURIComponent和decodeURIComponent
javascript
程序员小刘14 分钟前
如何优化React Native应用以适配HarmonyOS5?
javascript·react native·react.js·华为·harmonyos