Objektorientierte Programmierung in JavaScript
Anzeige Hier werben
Viele halten JavaScript noch immer für den Grundsatz alles Bösen das in
den letzten Jahren an Geblinke, Geblitze und anderen Gräueltaten die im
Internet kursierten. Seit dem Web 2.0 konnte JavaScript einiges an
Punkten gut machen und findet sich mittlerweile sogar in den Top 10 der beliebtesten Programmiersprachen.
Die Anwendungsgebiete fallen hauptsächlich in die DOM-Manipulation,
Effekte im Browser oder ähnliches. Ebenso hat JavaScript den schlechten
Ruf unsicher zu sein, welcher jedoch durch das Sandboxing um einiges
verringert wird (ActiveX-Elemente ausgenommen) und durch gute
Programmierung vernichtet wird.
JavaScript ist eine auf Objekten basierende Programmiersprache. Es gibt
zahlreiche vordefinierte Objekte wie z.B das String oder Window-Objekt.
Klassen und Konstruktor definieren
In JavaScript gibt es keine Klassen-Definition im herkömmlichen Sinne. Klassen werden erst einmal als einfache Funktionen erstellt.
Als Test-Klasse werden wir ein Auto verwenden und daran rumspielen.
1 2 3 | function Car(CarColor) {
this.CarColor = CarColor;
}
|
Das ist also unsere Klassen-Definition. Wie man sehen kann gibt es in JavaScript kein explizites Schlüsselwort für eine Klasse. JavaScript unterscheidet nur anhand der Initialisierung der Funktion ob es eine Klasse ist oder nicht.
Eine Klasse wird, wie in allen gängigen Programmiersprachen, mit dem
Schlüsselwort new
initialisiert.
1
2
3
4
5 | function Car(CarColor) {
this.CarColor = CarColor;
}
var Jeep = new Car('blue'); // Initialisierung des Objekts "Car"
alert(Jeep.CarColor); // Direkter Zugriff auf die Eigenschaft "CarColor"
|
Hier erstellen wir mittels new
ein
neues Objekt und übergeben dem Konstruktor den Parameter CarColor.
Ganz recht, die Funktion ist eigentlich unser Konstruktor. Anschließend
wird die öffentliche Eigenschaft CarColor
mit dem übergebenen
Parameter definiert und mittels alert
wird die Eigenschaft CarColor
am Bildschirm ausgegeben.
Datenkapselung von Methoden und Eigenschaften
Die Datenkapselung ist in der objektorientierten Programmierung
natürlich ein wichtiges und unabdingbares Feature das natürlich auch in
JavaScript nicht fehlen darf. In JavaScript existieren nur öffentliche
(public
) und private (private
) Eigenschaften und sogenannte
"privilegierte öffentliche Methoden", "nicht-privilegierte öffentliche
Methoden" und natürlich private Methoden.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | function Car(CarColor) {
// öffentliche (public) Eigenschaft
this.CarColor = CarColor;
// privilegierte öffentliche Methode
this.setCarColor = function(newCarColor) {
this.CarColor = newCarColor;
}
}
var Jeep = new Car('blue');
alert(Jeep.CarColor);
Jeep.setCarColor('orange');
alert(Jeep.CarColor);
|
Hier definieren wir die
"privilegierte öffentliche Methode" setCarColor
mit einem Parameter.
Beim Aufruf wird die "öffentliche Eigenschaft" CarColor
überschrieben
und anschließend wieder ausgegeben.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 | function Car() {
// private Eigenschaft
var CarTank = '100 Liter';
// privilegierte öffentliche Methode
this.setCarTank = function(newCarTank) {
CarTank = newCarTank; // Zuweisung des neuen Tankinhaltes
getCarTank(); // Aufruf der privaten Methode
}
var getCarTank = function() {
// Ausgabe der privaten Eigenschaft
alert(CarTank);
}
}
var Cabrio = new Car();
Cabrio.setCarTank('200 Liter');
alert(Cabrio.CarTank); // Liefert "undefined"
Cabrio.getCarTank(); // Liefert "is not a function"
|
Dieses Beispiel veranschaulicht die
Zugriffsrechte der einzelnen Methoden und Eigenschaften. Die
Eigenschaft CarTank
ist privat und kann von außen nicht aufgerufen
oder befüllt werden nur innerhalb der Klasse ist das hantieren mit der
Eigenschaft möglich. Selbiges für die Methode getCarTank
.
In JavaScript ist es möglich bestehende Methoden bzw. Objekte nachträglich zu beeinflussen. Dies funktioniert mittels sogenannten "Prototypen" auf die JavaScript basiert. Dies hat den Vorteil von mehr Unabhängigkeit und Flexibilität für den Programmierer.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 | function Car() {
// öffentliche Eigenschaft
this.CarName = "Audi";
// private Eigenschaft
var CarColor = "Black";
// private Methode
var setCarColor = function(newCarColor) {
CarColor = newCarColor;
}
// privilegierte öffentliche Methode
this.getCarInfosInside = function() {
setCarColor('Green');
alert("CarName:" + this.CarName + " CarColor:" + CarColor);
}
}
// nicht-privilegierte öffentliche Methode
Car.prototype.getCarInfosOutside = function() {
setCarColor('Green');
alert("CarName:" + this.CarName + " CarColor:" + CarColor);
}
var Audi = new Car();
Audi.getCarInfosInside(); // Liefert "Audi" und "Green"
Audi.getCarInfosOutside(); // Liefert "setCarColor" is not defined, "Audi" und "undefined"
|
Wie man hier gut sehen kann wird
einmal die "privilegierte öffentliche Methode" getCarInfosInside
aufgerufen (bitte entschuldigt meine Kreativen Methoden-Namen) und einmal die "nicht-privilegierte öffentliche Methode" getCarInfosOutside
. Die Methode in der Klasse hat natürlich vollen
Zugriff auf alles was drinnen so abläuft, d.h ich kann auf alle
Eigenschaften und Methoden zugreifen. Die Methode außerhalb der Klasse
kann lediglich auf öffentliche Eigenschaften und Methoden zugreifen.
Vererbung
Durch die Prototypen-Funktionen ist es möglich Vererbung in JavaScript zu benutzen.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 | // Superklasse
function Car(CarName) {
this.CarName = CarName;
this.CarWheels = "4";
}
// Subklasse
function Audi(CarName) {
// Dieser Konstruktor ruft den Konstruktor der Superklasse auf
this.constructor(CarName);
this.CarColor = 'Black';
this.getCarInfos = function() {
alert(this.CarName + " is " + this.CarColor + " and has " + this.CarWheels + " Wheels!");
}
}
Audi.prototype = new Car(); // Hier passiert die Vererbung
AudiA3 = new Audi('Audi A3');
Audi80 = new Audi('Audi 80');
AudiA3.getCarInfos(); // Liefert "Audi A3 is Black and has 4 Wheels"
Audi.prototype.setCarColor = function(newCarColor) {
this.CarColor = newCarColor;
this.getCarInfos();
}
Audi80.setCarColor('Yellow'); // Liefert "Audi 80 is Yellow and has 4 Wheels"
|
In diesem Beispiel haben wir eine
Superklasse Car
und die Subklasse Audi
. Car
besitzt 2 öffentliche
Eigenschaften. Eine wird per Parameter befüllt, die andere ist es
bereits. Audi
besitzt eine 2 privilegierte öffentliche Methoden, dass
sind this.constructor
und this.getCarInfos
. Wobei der Konstruktor
nur dafür da ist um die Superklasse aufzurufen ohne sie extra nochmal
initialisieren zu müssen. Anschließend passiert die Vererbung mittels
dem Prototypen. Dann definieren wir 2 verschiedene Audi's und lassen
uns per getCarInfos
die Audi A3-Daten ausgeben. Da wir alle
Eigenschaften von der Superklasse geerbt haben können wir auf den Namen
und die Anzahl der Reifen zusätzlich zugreifen.