Как предоставить пространства имен в JavaScript с экземплярами объектов

У меня есть JavaScript "объект", построенный следующим образом:

function foo()
{
    this.length = 0;
}

foo.prototype.getLength = function()
{
    return this.length;
}

...

Я знаю, как эмулировать пространства имен с одноэлементными объектами JavaScript, но каков наилучший способ «пространства имен» для объекта, такого как приведенный выше, который будет расширен?

Я знаю, что несколько библиотек JavaScript имеют возможности для именования, но я использую jQuery и предпочел бы не добавлять еще одну библиотеку. Я хотел бы быть в состоянии предоставить свою собственную, возможно, используя jQuery, внутреннюю схему пространства имен для моих объектов JS, которые необходимо создать.

Спасибо рп

22.08.2008 17:37:07
5 ОТВЕТОВ
РЕШЕНИЕ

Просто:

if(!MyNamespace) MyNamespace = {};

MyNamespace.foo = function() {
   this.length = 0;
};
MyNamespace.foo.prototype.getLength = function() {
   return this.length;
};
12
22.08.2008 18:18:30
@ Хамелеон - а? О чем ты говоришь?! «prototype» - это свойство автоматически, его не нужно «создавать» как таковое
Jason Bunting 10.11.2015 20:56:02

Не должно сильно отличаться:

namespace.foo = function foo() {...}
namespace.foo.prototype.getLength = function() { ... }

или вы могли бы использовать

(function() {
  function foo() { ... }
  foo.prototype...
  namespace.foo = foo;
})();

чтобы сохранить набор текста.

2
22.08.2008 17:41:59

Javascript на самом деле не имеет пространства имен или пакетов, как другие языки. Вместо этого у него есть замыкания. Если у вас есть приложение, состоящее из нескольких функций, переменных и объектов, вы должны поместить их в один глобальный объект. Это будет иметь тот же эффект, что и пространство имен.

Например:

var namespace = {
  this.foo: function(){
    ...
  },
  this.foo.prototype.getLength: function(){
    ...
  }
}

Вы также можете создать набор вложенных объектов и симулировать пакеты:

loadPackage = function(){
  var path = arguments[0];
  for(var i=1; i<arguments.length; i++){
    if(!path[arguments[i]]){
      path[arguments[i]] = {};
    }
    path = path[arguments[i]];
  }
  return path;
}

loadPackage(this, "com", "google", "mail") = {
  username: "gundersen",
  login: function(password){
    ...
  }
}
this.com.google.mail.login("mySecretPassword");
7
21.04.2017 10:19:05
Хорошие советы - но я думаю, вы хотите двоеточия вместо точек с запятой в первом примере, нет?
harpo 8.09.2009 18:09:24

Оба ответа были очень полезны! Вот чем я закончил:

if( typeof( rpNameSpace ) == "undefined" ) rpNameSpace = {};

rpNameSpace.foo = function() {
    this.length = 613;
}
rpNameSpace.foo.prototype.getLength = function() {
    return this.length * 2;
}

Затем, чтобы использовать получившийся объект namespaced:

var x = new rpNameSpace.foo()

display( x.getLength() );
2
21.04.2017 10:19:40

Другой альтернативой может быть среда bob.js :

bob.ns.setNs('myApp.myFunctions', { 
    say: function(msg) {  
        console.log(msg); 
    } 
}); 

//sub-namespace
bob.ns.setNs('myApp.myFunctions.mySubFunctions', { 
    hello: function(name) { 
        myApp.myFunctions.say('Hello, ' + name); 
    } 
}); 

//call:
myApp.myFunctions.mySubFunctions.hello('Bob'); 
-1
13.05.2013 15:26:50