10.1 Grundlagen des Polymorphismus
Polymorphismus ist eines der Schlüsselkonzepte der objektorientierten Programmierung (OOP). Im Allgemeinen ermöglicht Polymorphismus, dass Objekte verschiedener Klassen Daten verwenden, die über das gleiche Interface verarbeitet werden. Im Kontext von JavaScript bedeutet dies, dass verschiedene Objekte Methoden mit denselben Namen haben können, und diese Methoden können auf Objekten aufgerufen werden, ohne ihren konkreten Typ zu kennen.
Arten des Polymorphismus
In JavaScript sind die Hauptarten des Polymorphismus:
1. Ad-hoc Polymorphismus (ad-hoc polymorphism):
- Methodenpolymorphismus, Aufruf von Methoden mit dem gleichen Namen für Objekte unterschiedlicher Typen
- Beispiele umfassen die Überladung von Funktionen und Operatoren (was nicht direkt in JavaScript unterstützt wird, aber simuliert werden kann)
2. Subtyp-Polymorphismus (Subtype polymorphism):
- Subtyp- oder Inklusionspolymorphismus, wenn Objekte verschiedener Klassen, die von derselben Basisklasse erben, als Objekte der Basisklasse behandelt werden können
- Dies ist der Haupttyp des Polymorphismus, der durch Vererbung und Interfaces implementiert wird
Vorteile des Polymorphismus:
- Vereinfachung des Codes: Polymorphismus ermöglicht das Schreiben von flexiblerem und allgemeinerem Code, der mit verschiedenen Objekttypen arbeiten kann, ohne deren konkrete Typen zu kennen.
- Erweiterbarkeit: Polymorphismus erleichtert das Hinzufügen neuer Typen und Verhaltensweisen zu einem System, ohne den bestehenden Code ändern zu müssen.
- Unterstützung: Polymorphismus fördert eine bessere Aufgabentrennung und erhöht die Lesbarkeit und Wartbarkeit des Codes.
10.2 Beispiele für Polymorphismus in JavaScript
Subtyp-Polymorphismus durch Vererbung
Beispiel 1: Verarbeitung verschiedener Objekttypen über ein Interface
In diesem Beispiel nimmt die Funktion playWithAnimal ein Objekt vom Typ Animal und ruft die Methode makeSound auf. Die Objekte Dog und Cat, die von Animal erben, überschreiben die Methode makeSound, und bei jedem Objekt führt der Aufruf der Methode zu einem anderen Ergebnis.
class Animal {
makeSound() {
console.log('Some generic sound');
}
}
class Dog extends Animal {
makeSound() {
console.log('Woof!');
}
}
class Cat extends Animal {
makeSound() {
console.log('Meow!');
}
}
function playWithAnimal(animal) {
animal.makeSound();
}
const dog = new Dog();
const cat = new Cat();
playWithAnimal(dog); // Gibt aus: Woof!
playWithAnimal(cat); // Gibt aus: Meow!
10.3 Polymorphismus durch Interfaces (Duck Typing)
In JavaScript gibt es keine eingebaute Unterstützung für Interfaces wie in anderen Sprachen, z.B. TypeScript oder Java. Stattdessen wird ein Ansatz verwendet, der als "Duck Typing" bekannt ist. Das bedeutet, dass ein Objekt als interface-kompatibel betrachtet wird, wenn es die erforderlichen Methoden und Eigenschaften hat, unabhängig von seinem konkreten Typ oder seiner Vererbung.
Duck-Regel: Wenn etwas aussieht wie eine Ente, schwimmt wie eine Ente und quakt wie eine Ente, dann ist es wahrscheinlich auch eine Ente.
Beispiel 2: Verwendung von Duck Typing
In diesem Beispiel nimmt die Funktion takeOff jedes Objekt an, das eine Methode fly hat. Die Objekte Bird und Airplane implementieren die Methode fly, und daher können sie an takeOff übergeben werden.
class Bird {
fly() {
console.log('Flying...');
}
}
class Airplane {
fly() {
console.log('Jet engine roaring...');
}
}
function takeOff(flyingObject) {
flyingObject.fly();
}
const bird = new Bird();
const airplane = new Airplane();
takeOff(bird); // Gibt aus: Flying...
takeOff(airplane); // Gibt aus: Jet engine roaring...
10.4 Polymorphismus durch Funktionen
In JavaScript sind Funktionen erstklassige Objekte und können übergeben werden, um polymorphes Verhalten zu implementieren.
Beispiel 3: Polymorphismus durch Funktionen
In diesem Beispiel nimmt die Funktion greet eine andere Funktion als Argument und ruft diese auf. Dadurch können verschiedene Funktionen verwendet werden, um unterschiedliche Aktionen auszuführen.
function greetMorning() {
console.log('Good morning!');
}
function greetEvening() {
console.log('Good evening!');
}
function greet(greetingFunction) {
greetingFunction();
}
greet(greetMorning); // Gibt aus: Good morning!
greet(greetEvening); // Gibt aus: Good evening!
10.5 Polymorphismus durch Methodenüberladung (Simulation)
JavaScript unterstützt keine direkte Methodenüberladung wie einige andere Programmiersprachen. Es ist jedoch möglich, die Methodenüberladung mithilfe von Funktionsargumenten und deren Typenprüfung zu simulieren.
Beispiel 4: Simulation der Methodenüberladung
In diesem Beispiel nimmt die Methode add zwei Argumente an und führt verschiedene Aktionen basierend auf ihren Typen aus. Wenn die Argumente Zahlen sind, addiert die Methode sie. Wenn die Argumente Arrays sind, verbindet die Methode sie.
class Calculator {
add(a, b) {
if (typeof a === 'number' && typeof b === 'number') {
return a + b;
} else if (Array.isArray(a) && Array.isArray(b)) {
return a.concat(b);
} else {
throw new Error('Invalid arguments');
}
}
}
const calc = new Calculator();
console.log(calc.add(1, 2)); // Gibt aus: 3
console.log(calc.add([1, 2], [3, 4])); // Gibt aus: [1, 2, 3, 4]
GO TO FULL VERSION