JavaScript中原型和原型链

原型[prototype]:函数

为其余对象提供共享属性的对象。this

每一个函数都有一个原型(prototype)属性,这个属性是一个指针,指向一个对象,这个对象包含特定实例共享的一些属性和方法。spa

 

以例服人:prototype

这个例子说明了原型对象是共享的,而且是一个指针,而且对象的实例中也有指向prototype指向对象的指针。指针

function Animal(name) { this.name = name || "动物"; } Animal.prototype.runs = function() { console.log(this.name + ',跑起来了\n') } var dog = new Animal('小狗') dog.runs() //输出"小狗跑起来了"

// 下面增长的方法,dog对象可使用吗?
Animal.prototype.hi = function() {console.log('hi')} dog.hi() //输出"hi",说明原型属性是一个指针,指向一个共享对象,无论先添加的仍是后添加的方法都能调用

//dog做为一个Animal实例,他的__proto__属性和Animal.prototype指向同一个对象,因此才可使用原型的方法。
console.dir(dog) // 查看 dog.__proto__

// dog.__proto__ & Animal.prototype
console.log(dog.__proto__ === Animal.prototype) //true,有相同的指针地址

 

原生构造函数的原型对象[不单函数有原型对象]code

console.dir(Object.prototype)对象

console.dir(Array.prototype)blog

console.dir(String.prototype)继承

console.dir(Date.prototype)原型链

 

再看一个__proto__  &  prototype的例子

var obj = { } obj.toString() // "[object Object]"
 //obj 对象为何有 toString 方法? //由于 obj 对象是 Object 构造函数的实例,obj 对象的原型指针指向 Object.prototype 对象。console.log(obj.__proto__ === Object.prototype )

经过原型关系图理解:

 

再看一个函数的原型的例子

var obj = {name: 'jack'} function getName() { console.log(this.name) } // 问题:Animal.call 方法来自哪?
getName.call(obj)  //来自Function对象
 console.dir(getName) console.log(getName.__proto__ === Function.prototype)  //true
console.log(Function.prototype.__proto__  === Object.prototype)  //true

经过原型关系图理解

原型继承:

function Animal() { this.name = '动物' } Animal.prototype.runs = function() { console.log(this.name + ',跑起来了\n') return this } function Bird() { this.name = '鸟' } Bird.prototype = new Animal() //让Bird的原型等于Animal的实例,由于new Animal中有__proto__指向Animal.prototype的指向(沿着原型链寻找),此处也能够写为Bird.prototype = Animal.prototype Bird.prototype.fly = function() { console.log(this.name + ',飞走了\n') return this } function Crow(name) { this.name = name || '乌鸦' } Crow.prototype = new Bird() Crow.prototype.drink = function() { console.log(this.name + ',喝饱了水\n') return this } var crow = new Crow('一只可爱的小乌鸦') crow.drink().runs().fly() console.dir(crow)

输出结果:

 

 

原型总结:

每个构造函数都有一个和其对应的原型对象。

构造函数的 prototype 属性和其实例对象的 “__proto__” 属性指向同一个对象。

某构造函数的全部实例对象,共享一份原型对象。

全部的对象均可以经过 “__proto__” 属性,最终链接到 Object.prototype 对象。

构造函数用 prototype 来定义原型的属性和方法,实例对象用 “__proto__” 来查找原型的属性和方法。

当查找一个对象的属性或方法时,JS引擎会向上遍历其原型链,直到找到给定名称的属性为止。若是最终在 Object.prototype 对象仍然没有找到此属性或方法,则返回 undefined 值。

相关文章
相关标签/搜索