2008-08-09 6 views
16

Il y a quelques façons d'obtenir classe comme le comportement en javascript, semblent le plus courant d'être prototype basé comme ceci:Quel style utilisez-vous pour créer une "classe"?

function Vector(x, y, x) { 
    this.x = x; 
    this.y = y; 
    this.z = z; 
    return this; 
} 

Vector.prototype.length = function() { return Math.sqrt(this.x * this.x ...); } 

et les approches de fermeture similaire à

function Vector(x, y, z) { 
    this.length = function() { return Math.sqrt(x * x + ...); } 
} 

Pour diverses raisons ce dernier est plus rapide, mais j'ai vu (et j'écris souvent) la version prototype et j'étais curieux de savoir ce que les autres faisaient.

+0

Mes tests ont montré que l'approche basée sur la fermeture est plus lente. Vous devez instancier une fermeture séparée pour chaque objet. L'approche prototype partage les méthodes avec toutes les instances. –

Répondre

9

Il est préférable d'affecter des fonctions au prototype (pour les méthodes publiques) car toutes les instances de la classe partageront la même copie de la méthode. Si vous affectez la fonction dans le constructeur comme dans le second exemple, chaque fois que vous créez une nouvelle instance, le constructeur crée une nouvelle copie de la fonction de longueur et l'affecte à cette seule instance.

Cependant, cette dernière technique est utile si vous voulez chaque copie d'avoir sa propre copie, l'utilisation principale de cet être à faire des méthodes privées/privilèges qui ont accès à des variables privées déclarées dans le constructeur et héritées par la fermeture mécanisme. Douglas Crockford a une bonne summary

2

Eh bien, je n'ai pas vraiment d'opinion d'expert à ce sujet. Habituellement, je finis par utiliser l'approche basée sur les fermetures simplement parce que le code est plus simple à gérer. Mais, je me suis retrouvé à utiliser des prototypes pour des méthodes qui ont beaucoup de lignes de code.

2

Vous avez également le choix de:

function Vector(x, y, z) { 
    function length() { 
    return Math.sqrt(x * x + ...); 
    } 
} 

Ce qui est probablement aussi lent que par exemple deux, mais il ressemble plus à Java/C# et est un peu plus explicite.

3

Heureusement, je peux utiliser prototype.js, qui fournit de beaux wrappers. Ainsi, vous pouvez le faire:

var Person = Class.create({ 
    initialize: function(name) { 
     this.name = name; 
    }, 
    say: function(message) { 
     return this.name + ': ' + message; 
    } 
}); 

Prototype.js Documentation: Defining classes and inheritance

+0

Je ne pense pas que OP demandait un emballage qui cache les détails. Il voulait savoir pourquoi vous choisiriez l'une ou l'autre approche, afin qu'il puisse évaluer les avantages. –

4

Il est également l'objet approche du prototype littéral:

var Vector = function(){}; 

Vector.prototype = { 
    init:function(x,y,z) { 
    this.x = x; 
    this.y = y; 
    this.z = z; 
    }, 
    length:function() { 
    return Math.sqrt(x * x + ...); 
    } 
}; 

var v1 = new Vector(); 
v1.init(1,2,3); 
+0

Vous ne pouvez pas définir l'objet prototype littéral si vous héritez d'autre chose, cela remplacerait le prototype précédent –

+0

Vous avez raison, mais dans ce cas, "Vector" est un nouvel objet, je n'ai donc pas besoin de m'inquiéter des problèmes d'héritage – JayTee

1

Je suis un grand fan de l'utilisation John Resig's library pour cela. Léger, direct, et vous savez déjà comment l'utiliser si vous connaissez le style orienté objet «habituel».

1

Il n'y a pas de cours dans javascript.

Il existe cependant des objets. Vous n'avez pas besoin d'une classe pour créer un objet en javascript.Il possède des fonctions de constuctor que vous pouvez invoquer avec de nouveaux, par exemple:

var james = new Person(); 

Vous pouvez simuler la classe comme comportement avec:

exemple prototype:

function Car (type) { 
    this.type = type; 
    this.color = "red"; 
} 

Car.prototype.getInfo = function() { 
    return this.color + ' ' + this.type + ' car'; 
}; 

objet exemple littéral

var car = { 
    type: "honda", 
    color: "red", 
    getInfo: function() { 
     return this.color + ' ' + this.type + ' car'; 
    } 
} 
Questions connexes