14

在阅读了有关模块模式的一些内容后,我看到了一些返回您想要公开的属性的方法。

最常见的方法之一是在“return”语句中声明您的公共属性和方法,除了您的私有属性和方法。类似的方式(“Revealing”模式)是提供对您想要公开的属性和方法的简单引用。最后,我看到的第三种技术是在模块函数中创建一个新对象,在返回该对象之前为其分配新属性。这是一个有趣的想法,但需要创建一个新对象。

所以我在想,为什么不直接使用this.propertyName分配你的公共属性和方法,最后使用return this呢?这种方式对我来说似乎更简单,因为您可以使用通常的varfunction语法创建私有属性和方法,或者使用this.propertyName语法来声明您的公共方法。

这是我建议的方法:

(function() {

var privateMethod = function () {
    alert('This is a private method.');
}

this.publicMethod = function () {
    alert('This is a public method.');
}

return this;

})();

使用上述方法有什么优点/缺点吗?其他人呢?

4

5 回答 5

30

您的函数没有对象上下文,因此在这种情况下this引用全局对象。window您分配给this的每个属性都会自动污染全局命名空间。

(function() {
    console.log(this == window); // true

    this.publicMethod = function () {
        alert('This is a public method.');
    }

})();

console.log(publicMethod); // function()

你可以显式地传递一个对象来告诉它使用哪个上下文。

var MYAPP = {};

(function() {
    // 'this' will now refer to 'MYAPP'
    this.publicMethod = function () {
        alert('This is a public method.');
    }
}).call(MYAPP);

console.log(publicMethod); // undefined
console.log(MYAPP.publichMethod); // function()

你可以用其他风格写:

var MYAPP = (function(my) {
    var my;
    ⋮
    return my;
})(MYAPP);

我们到达了一个已经讨论过的模式有关更多详细信息,请参阅 Dustin 关于确定匿名函数范围的文章。

于 2010-04-26T12:39:07.987 回答
4

我会推荐您将公共属性和方法添加到然后返回的匿名对象的样式:

var myModule = (function() {
    function privateMethod() { ... }
    function publicMethod() { ... }

    return { publicMethod: publicMethod };
})();
于 2010-04-26T12:41:58.147 回答
2

如果要发布方法,请执行以下操作:

var export = (function() {

var privateMethod = function () {
  alert('This is a private method.');
}
var export = {};

export.publicMethod = function () {
  alert('This is a public method.');
}

return export;

})();
于 2010-04-26T12:42:56.543 回答
2

另一种选择是完全避免这个引用。定义一个创建并返回匿名对象的函数。

function makeThing(someAttribute) {
  var privateVariable = 42;

  function someMethod() {
    return privateVariable;
  }

  return {
    "publicMethodName": someMethod,
    "getAttribute": function() {
      return someAttribute;
    }
  };
}

var thing = makeThing(99);
thing.publicMethodName();
thing.getAttribute();
于 2010-04-26T19:06:31.563 回答
1

揭示模块模式:

var m1 = (function(){ return {method: mthod} })();
var m2 = new function Singleton(){ return {method: mthod} };
var m3 = ({}).prototype = {method: method};
var m4 = ({}).prototype = (function(){ ... })();
var m5 = (function(){}).prototype = {} || (function(){ ... })();

var m6 = (function(extendee){
    return extendee.prototype = {attr3: 'attr3'};
})({currentAttr1: 1, currentAttr2: 2});

此外,如果您需要方法链接:

var m = (function(){}).prototype = (function(){
    var thus = m;  // this
    console.log('m this-------', thus);

    function fn(){
        console.log('fn', thus);
        return thus;
    }
    function f(){
        console.log('f', thus);
        return 'poop';
    }

    return {f: f, fn: fn};
})();

console.log('M:', m, 'm.fn', m.fn(), 'm.fn.f', m.fn().f());

还有更多方法,您也可以突出您的模块。

于 2013-09-19T22:38:37.103 回答