假设我们有一个对象Person
如下:
function Person(name){
this.name = name;
this.greeting = function(){
alert("Hi I'm " + this.name);
}
}
及其子代
function Teacher(name, subject){
Person.call(this, name);
this.subject = subject;
Teacher.prototype = Object.create(Person.prototype);
}
我尝试如下重写greeting
方法:
Teacher.prototype.greeting = function(){
alert("Hello my name is " + this.name + " and I teach " + this.subject);
}
但是teacher1.greeting()
调用Person
的方法,而不是Teacher
的方法,如您在此处看到的:
答案 0 :(得分:1)
更新的答案: 现在,我在家中并在笔记本电脑上,我看到了该错误。您将教师原型放置在错误的位置。
所以您需要这样做:
// Incorrect
function Teacher(first, last, age, gender, interest, subject) {
Person.call(this, first, last, age, gender, interest);
this.subject = subject;
Teacher.prototype = Object.create(Person.prototype);
}
// Correct
function Teacher(first, last, age, gender, interest, subject) {
Person.call(this, first, last, age, gender, interest);
this.subject = subject;
}
Teacher.prototype = Object.create(Person.prototype);
因此,每次实例化Teacher
的新实例时,都将用Person
覆盖它的原型。因此,无论您将教师的原型设置为什么,它都会被覆盖。
答案 1 :(得分:0)
在Person函数原型的第一个类greeting
中。
如果在构造函数中使用this
,则引用的是新创建的对象,而不是函数的原型。如果要覆盖原型功能,这是正确的方法:
function Person(name){
this.name = name;
}
Person.prototype.greeting = function(){
alert("Hi I'm " + this.name);
}
您可以通过检查Person.prototype.greeting
的值将此代码与您的代码进行比较。
这就是为什么您不能用Teacher类覆盖它,原因是greeting
函数在每次创建Teacher对象并调用它的构造函数时都被Person构造函数覆盖。
答案 2 :(得分:0)
问题是您在greeting
中将Person
定义为 instance方法。它应该是Person.prototype
的方法。为什么?因为当您引用实例的属性时,解释器总是 first 首先检查实例属性的存在,因此然后实例的构造函数原型属性。
所以这应该起作用:
const someTeacher = new Teacher("Peter", "Jones", 26, "Male", "Functional Programming", "Math");
someTeacher.greeting();
function Person(first, last, age, gender, interest) {
this.name = {
first,
last
};
this.age = age;
this.gender = gender;
this.interest = interest;
// set the Person.prototype greeting method
// if not already done
if (!Person.prototype.greeting) {
Person.prototype.greeting = function() {
console.log("Hi I'm " + this.name.first);
};
}
}
function Teacher(first, last, age, gender, interest, subject) {
Person.call(this, first, last, age, gender, interest);
this.subject = subject;
// set Teachers prototype to Person
// if not already done
if (!Teacher.prototype.greeting) {
// override [greeting] first. If you do this after
// pointing the prototype to Person, it wil not
// work, probably because in that case you're
// overwriting Person.prototype.greeting which is
// a nogo
Teacher.prototype.greeting = function() {
console.log("Hello my name is " + this.name.first + " and I teach " + this.subject);
};
// set prototype to Person
Teacher.prototype = Person;
}
}