【问题标题】:JavaScript - Inheritance in ConstructorsJavaScript - 构造函数中的继承
【发布时间】:2012-06-26 19:59:02
【问题描述】:

对于一个 JavaScript 项目,我们希望引入对象继承来减少代码重复。但是,我不能完全按照我想要的方式运行它,需要一些帮助。

我们使用模块模式。假设有一个超级元素:

a.namespace('a.elements.Element');
a.elements.Element = (function() {
    // public API -- constructor
    Element = function(properties) {
        this.id = properties.id;
    };

    // public API -- prototype
    Element.prototype = {
        getID: function() {
            return this.id;
        }
    };

    return Element;
}());

还有一个继承自这个超级元素的元素:

a.namespace('a.elements.SubElement');
a.elements.SubElement = (function() {
    // public API -- constructor
    SubElement = function(properties) {
        // inheritance happens here
        // ???
        this.color = properties.color;
        this.bogus = this.id + 1;
    };

    // public API -- prototype
    SubElement.prototype = {
        getColor: function() {
            return this.color;
        }
    };

    return SubElement;
}());

您会注意到我不太确定如何实现继承本身。在构造函数中,我必须能够将参数传递给超级对象构造函数并创建一个超级元素,然后用于创建继承的元素。我需要一种(舒适的)可能性来访问新对象的构造函数中的超级对象的属性。理想情况下,我可以对超级对象进行操作,就好像它是新对象的一部分一样。

我还希望能够创建一个新的 SubElement 并在其上调用 getID()

我想要完成的似乎是传统的基于类的继承。但是,我想使用原型继承来做到这一点,因为那是 JavaScript 方式。这甚至可行吗?

提前致谢!

编辑:修复了 cmets 中建议的私有变量的使用。 EDIT2:代码的另一个更改:重要的是id 可以从SubElement 的构造函数中访问。

【问题讨论】:

  • 只是让您知道:您的“私有”变量id 将由所有实例共享,因此它是一个静态变量。每当您创建Element 的实例时,它将覆盖id 的当前值。你不能像这样使用原型函数和“私有”instance变量。
  • 模块模式与继承和 OOP 是分开的。闭包内的变量也不是对象的私有字段。
  • @Esailija:尽管按照 Crockford 的模式,它们经常被这样使用。但是闭包必须是对构造函数的调用,而不是对模块工厂的调用。 :-)
  • @Esailija: :-) 哦,还不错。不过,幸运的是,我们会及时收到true private properties
  • 你是对的,当然。我修好了。

标签: javascript inheritance


【解决方案1】:

如果您愿意,您可以使用 JavaScript 的原型继承来进行类类继承。 See this other answer 获取完整示例和讨论,您可以轻松地将其融入您的模式。

【讨论】:

  • 那么这个问题不应该作为副本关闭吗?
  • @FelixKling:我无法确定它是否真的是重复的。不同的问题,基本相同的答案。 :-) 我们需要的是规范的“你如何在 JavaScript 中进行基本继承?”题。也许上面提到的那个已经足够接近了……
  • 是的,我们绝对需要一个。我有一种感觉,我每隔一天就写一篇关于继承的文章。您的回答似乎涵盖了一切。
  • +1 让你出局,但可能会因为重复而被关闭。
  • 正是我所需要的。我想,我没有找到答案,因为我真的不知道我在寻找什么。谢谢!
【解决方案2】:

试试这段代码(继承方法取自here):

function inherit(proto) {
  function F() {};     
  F.prototype = proto;
  return new F();
}

a.namespace('a.elements.SubElement');
a.elements.SubElement = (function() {
    // private properties
    var color;

    // public API -- constructor
    SubElement = function(properties) {
        color = properties.color;
    };

    //inherit from parent
    SubElement.prototype = inherit(a.elements.Element);

    //add new methods to the prototype

    SubElement.prototype.getColor = function() {
            return color;
    }

    SubElement.prototype.doSomethinkWithID = function() {
            var id = this.getID();
    }

    return SubElement;
}());

【讨论】:

  • 感谢您的建议。但是,问题是,我无法访问我需要的SubElement 的构造函数中的超级元素的属性。我已经修复了我的代码以更清楚地说明这一点。对此感到抱歉。
猜你喜欢
  • 2013-09-17
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-06-04
  • 2023-03-07
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多