Die Überladung von Funktionen (Overloading) ist ein Mechanismus zur Deklaration mehrerer Funktionen mit demselben Namen, jedoch mit unterschiedlicher Signatur (Anzahl oder Typ von Parametern).
Standardwerte für Parameter können in der Deklaration von Funktionen angegeben werden. Feinheit: Standardwerte werden nur bei der Kompilierung des Aufrufs berücksichtigt und vom Compiler basierend auf der sichtbaren Signatur eingesetzt.
In Klassen tritt häufig die folgende Situation auf:
class Printer { void print(int n, char c = '*') { /* ... */ } void print(const std::string& s) { /* ... */ } }; Printer p; p.print(5); // ruft print(int n, char c = '*') auf, c = '*' p.print("Hi"); // ruft print(const std::string&) auf
Feinheiten:
void foo(int x, int y = 10); void foo(int x); foo(1); // Fehler: unklar, welche Funktion aufgerufen werden soll
Welcher Ort ist der einzige, an dem es erlaubt ist, einen Standardwert für eine Mitgliedsfunktion einer Klasse anzugeben?
Antwort: Der Standardwert für die Methode einer Klasse darf in der Deklaration der Methode innerhalb der Klasse (oder in der ersten Deklaration außerhalb der Klasse) angegeben werden, aber es ist nicht erlaubt, ihn sowohl in der Klasse als auch in der Implementierung anzugeben. Ansonsten tritt ein Fehler wegen mehrfacher Definition auf.
class X { void func(int x = 5); // Hier ist es erlaubt }; void X::func(int x) { /* ... */ } // Aber hier nicht!
Geschichte 1
In der Banksoftware gab es einen Fehler beim Kompilieren: ein Teil der überladenen Funktionen mit unterschiedlichen Standardwerten störte die eindeutige Auswahl, die Aufrufe waren während des Kompilierens mehrdeutig — Ergebnis, keine Möglichkeit, das Release zu erstellen, bis manuelle Korrekturen behoben wurden.
Geschichte 2
In dem Team gab es einen verbreiteten Stil, bei dem alle Standardwerte in die Implementierung und nicht in die Header-Datei der Klasse verschoben wurden, was jedoch bei einigen Methoden der Klassen zu Inkonsistenzen zwischen Schnittstelle und Implementierung führte — verschiedene TU sahen unterschiedliche Parameter der Funktion, was zu seltsamen Kompilierungs- und Laufzeitfehlern führte.
Geschichte 3
Bei der Erweiterung einer öffentlichen Bibliothek wurde versehentlich eine Überladung einer Funktion mit denselben Parametern, aber unterschiedlichen Standardwerten hinzugefügt. Der Compiler gab Mehrdeutigkeiten bei den API-Aufrufen aus, und Benutzer stießen auf veraltete Aufrufe und gebrochene binäre Kompatibilitäten.