We read every piece of feedback, and take your input very seriously.
To see all available qualifiers, see our documentation.
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
当你读到原型继承时,经常会看到如下定义:
当访问对象属性时,javascript将遍历原型链向上查找,直到找到该属性。
大多数javascript使用 __ proto __ 代表原型链中下一个对象,我们将会介绍 __ proto __ 与prototype的区别
Note: __ proto __ 是不标准的,不应在代码中使用。本文中用于解释javascript继承原理。
下面的代码显示了javascript引擎如何查找属性
function getProperty(obj,prop){ if( obj.hasOwnProperty(prop) ){ return obj[prop]; }else if(obj.__proto__ != null){ return arguments.callee(obj.__proto__,prop); }else{ return undefined; } }
让我们看一个普通的例子:一个2D点:有两个点坐标x、y和一个print方法 使用原型继承方式之前,我们创建一个有三个属性x、y、print的对象。为了创建一个新点,我们创建一个对象,该对象 __ proto __ 设置为point
var Point = { x:0, y:0, print:function(){ console.log(this.x,this.y); } }; var p = {x:10,y:20,__proto__:Point}; p.print(); //10,20
令人困惑的是,每个使用该定义解释javascript原型继承的人没有给出以上代码,而给出以下代码
function Point(x, y) { this.x = x; this.y = y; } Point.prototype = { print: function(){ console.log(this.x,this.y); } }; var p = new Point(10,20); p.print(); //10,20
这段代码完全不同于第一段代码,Point现在是一个函数,使用prototype属性和new操作符。
Brendan Eich想让javascript像传统的面向对象语言如java、c++。在那些语言中,我们使用new实例化一个类,所以他为javascript写了一个new操作符。
function New(f) { var n = {'__proto__':f.prototype}; //step 1 return function(){ f.apply(n,arguments); //step 2 return n; //step 3 } }
测试代码
function Point(x, y) { this.x = x; this.y = y; } Point.prototype = { print: function(){ console.log(this.x, this.y); } } var p1 = new Point(10, 20); p1.print(); //10 20 console.log( p1 instanceof Point ); //true var p2 = New(Point)(10, 20); p2.print(); //10 20 console.log( p2 instanceof Point ); //true
Note:__ proto __ 与prototype并不是等价的。__ proto __ 实际上是某个实体对象的属性,而prototype则是属于构造器函数的属性
javascript规范只给出了new操作符供我们使用。然后Douglas Crockford使用new操作符实现了真正的原型继承。他写了Object.create函数
Object.create = function(parent) { function F(){}; F.prototype = parent; return new F(); };
这个看上去很奇怪,但是真的很简单。它只是创建了一个新的对象,并将他的prototype属性指向了你所想要的。如果可以使用 __ proto __ ,也可以写成这样:
Object.create = function(parent) { return {'__proto__':parent}; }
以下代码为使用真正的原型继承实现的Point示例
var Point = { x:0, y:0, print:function(){ console.log(this.x,this.y); } }; var p = Object.create(Point); p.x = 10; p.y = 20; p.print(); //10 20
我们介绍了什么是原型继承以及javascript如何使用一种特定的方式实现它
然而,真正的原型继承实现(Object.create与 __ proto __ )存在一些缺点:
延伸阅读:
本文翻译自Vjeux
The text was updated successfully, but these errors were encountered:
好顶赞
Sorry, something went wrong.
分析的很透彻,点赞
No branches or pull requests
原型继承的定义
当你读到原型继承时,经常会看到如下定义:
大多数javascript使用 __ proto __ 代表原型链中下一个对象,我们将会介绍 __ proto __ 与prototype的区别
下面的代码显示了javascript引擎如何查找属性
让我们看一个普通的例子:一个2D点:有两个点坐标x、y和一个print方法
使用原型继承方式之前,我们创建一个有三个属性x、y、print的对象。为了创建一个新点,我们创建一个对象,该对象 __ proto __ 设置为point
javascript怪异的原型继承
令人困惑的是,每个使用该定义解释javascript原型继承的人没有给出以上代码,而给出以下代码
这段代码完全不同于第一段代码,Point现在是一个函数,使用prototype属性和new操作符。
new的原理是什么
Brendan Eich想让javascript像传统的面向对象语言如java、c++。在那些语言中,我们使用new实例化一个类,所以他为javascript写了一个new操作符。
new操作符接受一个F函数及其参数:new F(arguments),分为3个步骤:
解释代码如下:
测试代码
javascript中真正的原型继承
javascript规范只给出了new操作符供我们使用。然后Douglas Crockford使用new操作符实现了真正的原型继承。他写了Object.create函数
这个看上去很奇怪,但是真的很简单。它只是创建了一个新的对象,并将他的prototype属性指向了你所想要的。如果可以使用 __ proto __ ,也可以写成这样:
以下代码为使用真正的原型继承实现的Point示例
总结
我们介绍了什么是原型继承以及javascript如何使用一种特定的方式实现它
然而,真正的原型继承实现(Object.create与 __ proto __ )存在一些缺点:
延伸阅读:
本文翻译自Vjeux
The text was updated successfully, but these errors were encountered: