Y a-t-il un avantage à écrire des classes JavaScript et des espaces de noms de cette ...

if(typeof MyNamespace === 'undefined'){
    var MyNamespace = {};
}

(function(){
MyNamespace.MyClass = function(){
    this.property = 'foo'

    return this;
}
}());

Par rapport à cela ...

if(typeof MyNamespace === 'undefined'){
    var MyNamespace = {};
}

MyNamespace.MyClass = function(){
    this.property = 'foo'

    return this;
}

J'ai vu le premier modèle implémenté dans quelques bibliothèques et essayais de savoir s'il y avait un avantage supplémentaire à moins qu'une autre fonction ne soit déclarée à l'intérieur de la fonction anonyme dans le premier exemple.

6
jcreamer898 18 nov. 2011 à 00:55

4 réponses

Meilleure réponse

A votre question:

Oui, il y a une différence (et un avantage). Dans votre premier exemple, vous pouvez contrôler le contrôle d'accès (c'est-à-dire utiliser une version basée sur un prototype de variables et de fonctions membres publiques / privées). Par exemple:

var m = (function() {
    var o = {};
    o.myPublicProperty = 0; // can be accessed by instantiated object's calling code

    var myPrivateProperty = 1; // can't be accessed outside of this module

    o.myPublicFunction = function() {
        myPrivateFunction();
        return myPrivateProperty;
    };

    function myPrivateFunction() {
        ++myPrivateProperty;
        ++o.myPublicProperty;
    }

    o.getMyPrivateProperty = function() {
        return myPrivateProperty;
    }

    return o;
})();

console.log(m.myPublicProperty);       // 0
console.log(m.getMyPrivateProperty()); // 1
console.log(m.myPrivateProperty);      // undefined
console.log(m.myPublicFunction());     // increments
console.log(m.myPublicProperty);       // 1
console.log(m.getMyPrivateProperty()); // 2

http://jsfiddle.net/dbrecht/EQ4Tb/

Un peu hors sujet, mais c'est un peu étrange pour moi:

if(typeof MyNamespace === 'undefined'){
    var MyNamespace = {};
}

Pourquoi ne pas simplement utiliser: var MyNamespace = MyNamespace || {};?

11
Demian Brecht 17 nov. 2011 à 21:13

Pour le cas simple que vous avez montré, la fonction anonyme immédiatement exécutée n'offre aucun avantage.

Cependant, vous pouvez déclarer des variables ou d'autres fonctions à l'intérieur de la portée des fonctions anonymes et elles seraient effectivement privées de votre fonction MyClass. C'est donc un énorme avantage, et même si vous n'avez pas besoin de variables privées maintenant, vous pourriez plus tard pour pouvoir utiliser la fonction anonyme de toute façon ...

Notez également que placer une instruction var dans un if est un peu inutile car la déclaration (mais pas l'affectation) est "hissée" hors du bloc.

0
nnnnnn 17 nov. 2011 à 21:07

Ouais, des variables privées.

var MyNamespace = MyNamespace || {};

(function(){

    var priv_var = 'bar';

    MyNamespace.MyClass = function(){
        this.property = 'foo';

        //priv_var is accessible in here

        return this;
    }

}());

Contre:

var MyNamespace = MyNamespace || {};

var priv_var = 'bar';

MyNamespace.MyClass = function(){
    this.property = 'foo';

    //priv_var is accessible anywhere

    return this;
}
0
Geuis 17 nov. 2011 à 21:07

Je ne suis pas entièrement sûr des autres avantages, mais tout ce qui est déclaré dans la fonction anonyme restera dans cette portée, c'est-à-dire qu'il n'est pas déclaré dans la portée globale. Cela peut être avantageux.

0
Willem Mulder 17 nov. 2011 à 21:01
8174172