没有'new'关键字的JavaScript继承

时间:2011-06-30 13:33:14

标签: javascript inheritance

我习惯在我的代码中使用这种模式,我喜欢它:

var UserWidget = (function(){
    var url = "/users",
        tmpl = "#users li", $tmpl;

    function load() {
        $tmpl = $(tmpl);
        $.getJSON(url, function(json){
            $.each(json, function(i, v) {
                appendUser(v);            
            });
        });
    }

    ...
    return {
        load: load
    };
})();

但是,我有很多“小部件”对象。 “ProfileWidget”,“PlayerWidget”等等,每个小部件共享的某些动作。理想情况下,如果我们以面向对象的方式思考,我希望每个widget对象都从主“Widget”类继承一些方法。

如果不改变我一直在使用的这种可爱模式,我怎么能这样做呢?

为了更清楚,我希望能够做到这样的事情:

var Widget = (function() {
    function init() {
        console.log("wow yeah");
    }
})();

// have UserWidget inherit somehow the Widget stuff
var UserWidget = (function() { ...

UserWidget.init(); // -> "wow yeah"

5 个答案:

答案 0 :(得分:3)

请记住,这些解决方案并非我通常所建议的,而只是为了满足这个问题。

如何关闭所有内容,以便可以从“子类”(demo

访问它
var Widget = (function () {

    var init = function () {
        console.log("wow yeah");
    };

    var User = (function () {

        var load = function () {
            init();
        };

        return {
            'load': load
        };
    } ());

    return { 'User': User };
} ());

// Usage: This loads a user and calls init on the "base"
Widget.User.load();

您可能喜欢的另一种方式(demo)只是使用正确的继承,但在闭包内然后返回该新函数的一个且仅一个实例。这种方式可以让你保持用户和其他任何对象

// Closing around widget is completely unneccesarry, but 
//    done here in case you want closures and in case you 
//    dont want another instance of widget
var Widget = (function () {

    // definition that we'll end up assigning to Widget
    function widget() {
           console.log("base ctor");
    }

    // sample method
    widget.prototype.init = function () {
        console.log("wow yeah");
    };

    // put widget in Widget
    return widget;
} ());

var User = (function () {

    function user() { }
    user.prototype = new Widget();

    // TODO: put your User methods into user.prototype

    return new user();
} ());

var Player = (function () {

    function player() { }
    player.prototype = new Widget();

    // TODO: put your Player methods into player.prototype

    return new player();

} ());

User.init();
Player.init();

答案 1 :(得分:2)

我决定使用Crockford's object

// function from Douglas Crockford, comments from me
function object(o) {
    // define a new function
    function F() {}
    // set the prototype to be the object we want to inherit 
    F.prototype = o;
    // return a new instance of that function, copying the prototype and allowing us to change it without worrying about modifying the initial object
    return new F();
}

// Usage:
var Widget = (function() {
    function init() {
        console.log("wow yeah");
    }
    return {
        init: init 
    };
})();

var UserWidget = (function() {
    var self = object(Widget); // inherit Widget
    function priv() {}
    self.pub = "boom";
    ...

    return self;
})();

UserWidget.init() // -> "wow yeah"

这对我很有用,我喜欢它!

答案 2 :(得分:0)

不使用new,您必须使用__proto__ property而不是prototype,因此这不适用于所有浏览器。

var Widget = {
    init: function () {
        console.log("wow yeah");
    }
};

var UserWidget = (function(){
    var url = "/users",
        tmpl = "#users li",
        $tmpl;

    function load() {
        $tmpl = $(tmpl);
        $.getJSON(url, function(json){
            $.each(json, function(i, v) {
                appendUser(v);            
            });
        });
    }

    return {
        load: load
    };
})();

UserWidget.__proto__ = Widget;

UserWidget.init();

演示:http://jsfiddle.net/mattball/4Xfng/

答案 3 :(得分:0)

您可以使用Object.create(obj),我认为这是您正在寻找的。

答案 4 :(得分:0)

以下是JS中原型设计的一个简单示例...有关此主题的更多详细信息,请阅读“JavaScript:好的部分”

// widget definition
var Widget = {
    init: function () {
        alert('wow yeah!');
    }
};
// user widget definition
var UserWidget = function () { };
UserWidget.prototype = Widget;
UserWidget.prototype.load = function () { alert('your code goes here'); }

// user widget instance
var uw = new UserWidget();
uw.init(); // wow yeah!
uw.load(); // your code goes here

希望这有帮助!