在JavaScript中构建构造函数时,最佳做法是什么?

时间:2015-10-17 07:17:54

标签: javascript inheritance

所以我一直试图在Javascript中找出原型继承,但我仍然对一点感到困惑。让我们说我想为一个拥有它自己的一些功能的人创建一个构造函数。

function Person(name) {
  this.name = name;
  this.sayName = function() {
    console.log("My name is " + name);
  }
}

var john = new Person("John");

john.sayName();

所以在这种情况下,我创建了一个对象并调用了一个函数,但这似乎并不是一种有效的方法。我已经看到的另一个例子就是:

function Person(name) {
  this.name = name;
}
Person.prototype.sayName = function() {
  console.log("My name is " + name);
}

var john = new Person("John");

john.sayName();

现在我已经读过第二个对象更有效率,因为它没有将sayName函数存储在自身内,而是在原型链中上升,直到它在Persons原型对象中找到它为止

我不确定的是我应该用于复杂的构造函数。在我看来,第一个片段比第二个片段更容易阅读,因为它有一个清晰的层次结构,但第二个片段据说效率更高。

在现实世界的场景中,我更有可能使用哪种构造函数?

编辑:我有一个跟进问题。有没有办法让第二个片段更具可读性?

4 个答案:

答案 0 :(得分:0)

如果您使用第一个,那么每次调用构造函数时,您将为sayName创建一个新的函数对象,而在第二种方法中,您可以避免这种开销。

如果你在构造函数中使用引用类型,它将被共享, 例如:

    function Person(name){
    this.name = name;
    this.hobbies = [..some hobbies];
}

现在爱好将由您使用此构造函数创建的每个对象共享,因此最好将共享属性放在原型上,并且只使用构造函数中的唯一对象

答案 1 :(得分:0)

通常,如果您要创建一个将从中创建多个实例的类,则应将方法添加到原型对象中。我相信的主要原因是类的所有实例都会引用原型对象,并且不会复制它。因此,如果原型对象发生变化,它将反映在所有实例引用的原型对象中。

这比在每个实例上创建(复制)每个方法的第一个选项更好。所以很多实例也意味着会创建很多这些方法,占用内存。但在第二个选项中,它们都使用在原型对象上创建的单个方法。

答案 2 :(得分:0)

在第一种方法中,将为每个实例创建方法函数。在第二个实例中,所有实例共享原型中定义的方法。所以第二种方法更好,因为节省了内存。

然而,ECMAScript 6几个月前正式发布,所以为什么不尝试class

class Person {
  constructor(name) {
    this.name = name;
  }

  sayName() {
    console.log("My name is " + this.name);
  }
}

var john = new Person("John");
john.sayName(); // "My name is John"

该功能尚未得到很好的支持,如果您希望在浏览器中向后兼容,请使用Babel

答案 3 :(得分:0)

ECMAScript 5中为类的创建实例引入的另一种语法是:

$("#slider").on("slid.bs.carousel", function()
{
    var that = this;
    var nextItem = $("#slider").find("div.active").next(".item");
    if(!nextItem.length)
    {
        nextItem = $(".active.item").siblings(":first");
    }
    var nextImage = nextItem.find("img");
    if(nextImage.hasClass("lazy-load"))
    {
        var src = nextImage.attr("data-src");
        nextImage.removeClass("lazy-load");
        nextImage.attr("src", src);
    }

    //the following code must be executed after nextImage is loaded:
    $(nextImage).on("load",function(){
        clearTimeout(t);

        $("#slider").carousel("pause");

        var duration = $(that).find("div.active").attr("data-interval");
        t = setTimeout(function() { $("#slider").carousel({interval: 1000}); }, duration-1000);
    });

});

示例:

Object.create(prototype [, propertiesObject ] )

如果您有兴趣学习有关javascript的高级内容,我建议使用一本名为"掌握Javascript设计模式的书#34;。