【问题标题】:Why can't I override the method definition in the class(function) description?为什么我不能覆盖类(函数)描述中的方法定义?
【发布时间】:2015-09-20 00:46:21
【问题描述】:

我不太明白,为什么我在第一条日志消息Prototype: [object Object],第二条是Prototype: New Plant

function Plant() {
this.toString = function() {
        return "Plant";
    }
}

function Fruit(name) {
    Plant.call(this);
    this.name = name;
    this.toString = function() {
        return "Fruit";
    }
}
Fruit.prototype = Object.create(Plant.prototype);     
var apple = new Fruit("apple");

console.log("Prototype: " + Object.getPrototypeOf(apple));
Plant.prototype.toString = function() {
    return "New Plant";
}
console.log("Prototype: " + Object.getPrototypeOf(apple));

我想既然我在 Plant 类中定义了 toString() 方法,那么所有 Fruit 实例也会有这个方法吗?

【问题讨论】:

    标签: javascript inheritance overriding prototype


    【解决方案1】:

    您的所有 Fruit 实例确实都可以访问 Plant 原型上的 .toString() 方法。但是,该方法被 Fruit 构造函数中的直接赋值覆盖。一旦 Fruit 构造函数为 this.toString 分配了一些东西,那将始终在原型链中隐藏 .toString()

    请记住,在 Fruit 构造函数的代码中,this 指的是新创建的实例。因此,对 this 属性的赋值是直接存在于每个实例上的属性。

    在像x.toString() 这样的任何表达式中,对名称为“toString”的属性的搜索从对象本身开始。如果在那里找到,则根本不参考原型链。

    现在,关于为什么您的 console.log() 语句会打印它们所做的其他问题,请注意 first 调用发生在您放置 .toString() 方法之前在工厂原型上。完成此操作后,在对 console.log() 的调用中的 + 表达式中发生的从对象到字符串的转换将隐式调用该函数以将原型对象转换为字符串。

    【讨论】:

    • 非常感谢您的回复!但是,如果我从 Fruit 函数中删除 toString() 描述,我在第一次调用 Object.getPrototypeOf(apple) 时仍然有相同的响应 - 它是 Prototype: [object Object]。不应该是“Plant”,因为搜索将遵循从 Fruit 到 Plant 的原型链,并且我在 Plant 函数中有 toString() 吗?
    • @AntonPoliakov 是的 - 因为您使用 Object.getPrototypeOf(apple)+ 运算符,并且将调用来自对象原型函数的默认 .toString(),并返回 [object Object]。请记住,原型对象本身是一个对象,prototype 对象中唯一可用的.toString()Object.prototype 上的那个。 Fruit instances 获得 .toString() 函数的事实并不重要。
    • 知道了。再次感谢!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-07-03
    • 1970-01-01
    • 1970-01-01
    • 2018-05-02
    相关资源
    最近更新 更多