如何在JavaScript中创建命名空间,使我的对象和函数不被其他同名对象和函数覆盖?我使用了以下方法:

if (Foo == null || typeof(Foo) != "object") { var Foo = new Object();}

有没有更优雅或更简洁的方式来做到这一点?


当前回答

另一种方式是,我认为它比对象文字形式限制少一点,是这样的:

var ns = new function() {

    var internalFunction = function() {

    };

    this.publicFunction = function() {

    };
};

上面的模式非常类似于模块模式,不管你喜欢与否,它允许你将所有函数公开为public,同时避免了对象字面量的刚性结构。

其他回答

JavaScript默认情况下不支持命名空间。因此,如果您创建任何元素(函数、方法、对象、变量),那么它将变成全局的,并污染全局命名空间。让我们以定义两个没有任何名称空间的函数为例,

function func1() {
    console.log("This is a first definition");

}
function func1() {
    console.log("This is a second definition");
}
func1(); // This is a second definition

它总是调用第二个函数定义。在这种情况下,命名空间将解决名称冲突问题。

在将我的几个库移植到不同的项目中,并且不得不不断更改顶级(静态命名的)名称空间之后,我转而使用这个小的(开源的)帮助函数来定义名称空间。

global_namespace.Define('startpad.base', function(ns) {
    var Other = ns.Import('startpad.other');
    ....
});

关于好处的描述在我的博客文章中。您可以在这里获取源代码。

我非常喜欢的一个好处是模块之间相对于加载顺序的隔离。你可以在加载外部模块之前引用它。当代码可用时,将填充您获得的对象引用。

我通常在闭包中构建它:

var MYNS = MYNS || {};

MYNS.subns = (function() {

    function privateMethod() {
        // Do private stuff, or build internal.
        return "Message";
    }

    return {
        someProperty: 'prop value',
        publicMethod: function() {
            return privateMethod() + " stuff";
        }
    };
})();

自从写了这篇文章以来,我的风格在这些年里有了微妙的变化,现在我发现自己是这样写闭包的:

var MYNS = MYNS || {};

MYNS.subns = (function() {
    var internalState = "Message";

    var privateMethod = function() {
        // Do private stuff, or build internal.
        return internalState;
    };
    var publicMethod = function() {
        return privateMethod() + " stuff";
    };

    return {
        someProperty: 'prop value',
        publicMethod: publicMethod
    };
})();

通过这种方式,我发现公共API和实现更容易理解。将return语句视为实现的公共接口。

我认为对于这样一个简单的问题,你们都使用了太多的代码。 没必要为它回购。 这是一个单线函数。

namespace => namespace.split(".").reduce((last, next) => (last[next] = (last[next] || {})), window);

试试吧:

//——定义—— Const namespace = name => name.split(".")。减少(下)(最后,= >(去年[下]=(去年[下一个 ] || {})), 窗口); //——使用---- Const c =命名空间("a.b.c"); c.MyClass = class MyClass {}; //—参见---- Console.log ("a: ", a);

在JavaScript中,没有预定义的方法来使用名称空间。在JavaScript中,我们必须创建自己的方法来定义NameSpaces。下面是我们在Oodles技术中遵循的一个过程。

注册命名空间 下面是注册名称空间的函数

//Register NameSpaces Function
function registerNS(args){
 var nameSpaceParts = args.split(".");
 var root = window;

 for(var i=0; i < nameSpaceParts.length; i++)
 {
  if(typeof root[nameSpaceParts[i]] == "undefined")
   root[nameSpaceParts[i]] = new Object();

  root = root[nameSpaceParts[i]];
 }
}

要注册一个命名空间,只需调用上述函数,参数为名称空间,以'分隔。”(点)。 例如 让您的应用程序名称为oodles。可以通过以下方法创建命名空间

registerNS("oodles.HomeUtilities");
registerNS("oodles.GlobalUtilities");
var $OHU = oodles.HomeUtilities;
var $OGU = oodles.GlobalUtilities;

基本上,它会在后端创建你的命名空间结构,如下所示:

var oodles = {
    "HomeUtilities": {},
    "GlobalUtilities": {}
};

在上面的函数中,您注册了一个名为“oodles”的命名空间。homeuutilities”和“oodles.GlobalUtilities”。为了调用这些命名空间,我们创建了一个变量,即var $OHU和var $OGU。

这些变量只是初始化名称空间的别名。 现在,当你声明一个属于HomeUtilities的函数时,你会像这样声明它:

$OHU.initialization = function(){
    //Your Code Here
};

上面是函数名初始化,并将其放入命名空间$OHU中。并在脚本文件中的任何地方调用此函数。只需使用下面的代码。

$OHU.initialization();

类似地,对于另一个NameSpaces。

希望能有所帮助。