Interessant ist auch der Unterschied zwischen Funktionen und Funktionen ohne Prototyp. Betrachten Sie eine alte Stildefinition:
void f(a)
float a; {
}
In diesem Fall lautet die aufrufende Konvention, dass alle Argumente heraufgestuft werden, bevor sie an die Funktion übergeben werden (z. B. wird ein float
Argument zuerst heraufgestuft double
, bevor es übergeben wird). Wenn also f
ein double
Parameter empfangen wird , der Parameter jedoch einen Typ hat float
(der vollkommen gültig ist), muss der Compiler vor der Ausführung des Funktionskörpers Code ausgeben, der das Double in einen Float konvertiert.
Wenn Sie einen Prototyp einfügen, führt der Compiler solche automatischen Heraufstufungen nicht mehr durch, und alle übergebenen Daten werden wie durch Zuweisung in die Parametertypen des Prototyps konvertiert. Folgendes ist also nicht legal und führt zu undefiniertem Verhalten:
void f(float a);
void f(a)
float a; {
}
In diesem Fall würde die Definition der Funktion den übermittelten Parameter von double
(das heraufgestufte Formular) in konvertieren , float
da die Definition im alten Stil ist. Der Parameter wurde jedoch als Float übergeben, da die Funktion einen Prototyp hat. Zum Beispiel gibt Clang
main.c: 3: 9: Warnung: Der heraufgestufte Typ 'double' des K & R-Funktionsparameters ist nicht kompatibel mit dem in einem früheren Prototyp deklarierten Parametertyp 'float' [-Wknr-geworbener-Parameter]
Sie haben folgende Möglichkeiten, um die Widersprüche zu lösen:
void f(double a);
void f(a)
float a; {
}
void f(float a);
void f(float a) {
}
Option 2 sollte bevorzugt werden, wenn Sie die Wahl haben, da die alte Stildefinition von vornherein entfernt wird. Wenn solche widersprüchlichen Funktionstypen für eine Funktion in derselben Übersetzungseinheit angezeigt werden, werden Sie normalerweise vom Compiler darüber informiert (dies ist jedoch nicht erforderlich). Wenn solche Widersprüche über mehrere Übersetzungseinheiten hinweg auftreten, bleibt der Fehler möglicherweise unbemerkt und kann zu schwer vorhersehbaren Fehlern führen. Es ist am besten, diese alten Stildefinitionen zu vermeiden.