2009-11-20 10 views
7

Was ist ein Prototyp für eine JavaScript-Klasse? Mit anderen Worten, was ist der Unterschied zwischenWas sind Prototypen in JavaScript?

Example.prototype.method {} 

und

Example.method{} 

wenn der Beispielklasse definieren?

Edit: Für Interessenten, fand ich eine große Erklärung (zusätzlich zu der Antwort unten) hier für die Differenz zwischen Klassenmethoden und Konstruktormethoden: http://idhana.com/2009/07/13/constructor-vs-class-methods-in-javascript/

Edit 2: Die vollständige Antwort! http://blog.anselmbradford.com/2009/04/09/object-oriented-javascript-tip-creating-static-methods-instance-methods/

Antwort

5

Der Unterschied besteht im letzteren Beispiel darin, dass Sie eine statische Methode erstellen, die nicht vererbt wird, wenn Example eine Konstruktorfunktion ist. Durch das Definieren von Eigenschaften in der prototype-Eigenschaft einer Konstruktorfunktion und das Erstellen von Objekten mit dem Schlüsselwort new erben die neu erstellten Objekte den Prototyp des Konstruktors und haben somit Zugriff auf diese Methoden.

Ein Beispiel wäre die Methoden in den Einbau-Kernbauer definiert sein, wie String .. neu erstellen Strings hat eine indexOf Methode, weil es einen in der Prototyp der definiert war String Funktion Konstruktor

typeof String.prototype.indexOf // 'function' 

var name = 'John'; 
alert(name.indexOf('J')) // 0 

Die Code unten erstellt einen Funktionskonstruktor, wir definieren zuerst eine statische Methode, erstellen ein Objekt, finden heraus, dass das Objekt keine getName-Methode hat, dann definieren wir eine im Prototyp und finden, dass das Objekt jetzt eine getName-Methode hat.

function Name(name) { 
    this.name = name; 
}; 
Name.getName = function(){}; 

var john = new Name(); 
typeof john.getName // undefined 

var john = new Name(); 
Name.prototype.getName = function(){ alert(this.name)}; 
typeof john.getName 

john.constructor.prototype.getName == john.getName // true 

So zu wiederholen, Vererbung in ECMAScript in erster Linie durch die Definition von Eigenschaften/Methoden in dem Prototyp einer Funktion Konstruktor erreicht wird, würde beispielsweise alle Kernbauern wie Datum/Anzahl/String sein, die Methoden in ihrem definiert haben entsprechende Prototypeigenschaften, mit denen Sie diese Methoden beim Erstellen einer Instanz mit dem Schlüsselwort new verwenden können.

Denken Sie daran, dass das neu erstellte Objekt eine constructor -Eigenschaft aufweist, die auf den Konstruktor verweist, der es erstellt hat, und auf die Eigenschaft prototype direkt zugreifen können. Das von uns erstellte Objekt john besitzt nicht direkt die getName-Methode, da der Interpreter es nicht direkt auf dem Objekt finden kann, das es nach oben zum Konstruktor bewegt, und findet es in seinem Prototyp.

Und übrigens, wir mussten nicht wirklich eine neue Instanz des john Objekts erstellen, wie in der anderen Antwort gezeigt, können Sie Eigenschaften im Prototyp definieren, nachdem Sie den ursprünglichen Konstruktor erstellt haben und alle Objekte dieses Prototyp erben würden Eigenschaften, auch nachdem sie erstellt wurden.

kann eine statische Methode nicht auf Kontext verlassen, auf einer bestimmten Instanz einer Klasse verlassen können nicht auf der this Stichwort verlassen können daher nicht wäre dies eine statische Methode nicht:

function Name(name) { 
    this.name = name; 
    this.getName = function() { return this.name; } 
}; 

Dies würde ein Beispiel für eine statische Methode sein:

Name.getName = function() {}; 

aber es gibt absolut keinen Sinn machen getName statisch, weil, wie der Name es schon sagt auf eine Objektinstanz verlassen müssen, um zu bestimmen, was der Name Eigenschaft ist, sollten Sie mehr gener haben ic-Hilfsfunktionen wie das Analysieren von Funktionen wie Date.parse als statische Methoden und Definieren von Instanzmethoden im Prototyp, da sie effizienter sind als this.foo = function(){} im Konstruktor definieren.

+0

Also wann würde ich Name.getName = function() {} verwenden? – sepiroth

+0

oder besser, wann könnte ich Methoden (und wie) für die Name-Klasse definieren, ohne die Prototyp-Definition zu verwenden? – sepiroth

+0

'getName' wäre eine öffentliche Methode, also definieren Sie sie auf dem Prototyp anstatt statisch, Sie würden eine statische Methode definieren, wenn es keinen Zweck hat, sie öffentlich zu machen oder im Prototyp. –

2

Ein Prototyp ist wie eine Klassendefinition, aber er kann dynamisch geändert werden. Wenn Sie ein Objekt eines bestimmten Typs instanziieren, verwendet es den Prototyp als Vorlage.

Wenn Sie einen Prototyp ändern, haben Objekte dieses Typs diese Änderungen.

Verwandte Themen