javascript - JavaScript .prototype 是如何工作的?

标签 javascript dynamic-languages prototype-oriented

我不太喜欢动态编程语言,但我编写了相当多的 JavaScript 代码。我从来没有真正理解过这种基于原型(prototype)的编程,有人知道它是如何工作的吗?

var obj = new Object();
obj.prototype.test = function() { alert('Hello?'); };
var obj2 = new obj();
obj2.test();

我记得不久前我与人们进行了很多讨论(我不确定我在做什么),但据我了解,没有类的概念。它只是一个对象,这些对象的实例是原始对象的克隆,对吧?

但是 JavaScript 中这个“.prototype”属性的确切用途是什么?它与实例化对象有何关系?

更新:正确方法

var obj = new Object(); // not a functional object
obj.prototype.test = function() { alert('Hello?'); }; // this is wrong!

function MyObject() {} // a first class functional object
MyObject.prototype.test = function() { alert('OK'); } // OK

还有这些 slides真的帮了大忙。

最佳答案

在 Java、C# 或 C++ 等实现经典继承的语言中,您首先创建一个类(对象的蓝图),然后您可以从该类创建新对象,或者您可以扩展该类,定义一个新的增强原始类的类。

在 JavaScript 中,您首先创建一个对象(没有类的概念),然后您可以扩充自己的对象或从中创建新对象。这并不难,但对于习惯了经典方式的人来说有点陌生且难以代谢。

例子:

//Define a functional object to hold persons in JavaScript
var Person = function(name) {
  this.name = name;
};

//Add dynamically to the already defined object a new getter
Person.prototype.getName = function() {
  return this.name;
};

//Create a new object of type Person
var john = new Person("John");

//Try the getter
alert(john.getName());

//If now I modify person, also John gets the updates
Person.prototype.sayMyName = function() {
  alert('Hello, my name is ' + this.getName());
};

//Call the new method on john
john.sayMyName();

到目前为止,我一直在扩展基础对象,现在我创建另一个对象,然后从 Person 继承。

//Create a new object of type Customer by defining its constructor. It's not 
//related to Person for now.
var Customer = function(name) {
    this.name = name;
};

//Now I link the objects and to do so, we link the prototype of Customer to 
//a new instance of Person. The prototype is the base that will be used to 
//construct all new instances and also, will modify dynamically all already 
//constructed objects because in JavaScript objects retain a pointer to the 
//prototype
Customer.prototype = new Person();     

//Now I can call the methods of Person on the Customer, let's try, first 
//I need to create a Customer.
var myCustomer = new Customer('Dream Inc.');
myCustomer.sayMyName();

//If I add new methods to Person, they will be added to Customer, but if I
//add new methods to Customer they won't be added to Person. Example:
Customer.prototype.setAmountDue = function(amountDue) {
    this.amountDue = amountDue;
};
Customer.prototype.getAmountDue = function() {
    return this.amountDue;
};

//Let's try:       
myCustomer.setAmountDue(2000);
alert(myCustomer.getAmountDue());

var Person = function (name) {
    this.name = name;
};
Person.prototype.getName = function () {
    return this.name;
};
var john = new Person("John");
alert(john.getName());
Person.prototype.sayMyName = function () {
    alert('Hello, my name is ' + this.getName());
};
john.sayMyName();
var Customer = function (name) {
    this.name = name;
};
Customer.prototype = new Person();

var myCustomer = new Customer('Dream Inc.');
myCustomer.sayMyName();
Customer.prototype.setAmountDue = function (amountDue) {
    this.amountDue = amountDue;
};
Customer.prototype.getAmountDue = function () {
    return this.amountDue;
};
myCustomer.setAmountDue(2000);
alert(myCustomer.getAmountDue());

虽然我不能在 Person 上调用 setAmountDue()、getAmountDue()。

//The following statement generates an error.
john.setAmountDue(1000);

关于javascript - JavaScript .prototype 是如何工作的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/572897/

相关文章:

javascript - 如何在不调用其构造函数的情况下复制对象及其原型(prototype)链?

javascript - javascript中的原型(prototype)行为

javascript - 你能在 Angular 中从一个作用域访问另一个作用域的变量吗

javascript - 添加产品后更新 Woocommerce 购物车 (jQuery)

html - 返回 JS 函数的值并将其用作输入按钮的值

programming-languages - 您可以使用哪些语言即时动态重写函数?

actionscript-3 - 以编程方式添加属性来执行ActionScript对象(元编程)

javascript - float 页脚仅在用户向下滚动 200 像素后出现

python - 如何创建具有属性的内联对象?