Wie andere haben bereits gesagt, ein int
zu printf
vorbei, wenn es eine double
Ursachen undefiniert Verhalten erwartet, und alles, was passieren könnte. Vielleicht interessiert dich der Grund warum das Programm druckt 98.979980
auf der dritten Zeile und nicht irgendeine Zufallszahl.
Argumente werden printf
auf dem Stapel übergeben. Wenn die Leitung 2 98.98
an printf
übergibt, wird sie auf den Stapel geschoben, wobei der niedrigstwertige Teil der Nummer zuerst ist.
Dann printf
kehrt zurück, und in der dritten Zeile wird es erneut aufgerufen, jetzt mit 98
auf den Stapel geschoben. Auf Ihrer Architektur scheint der int
Typ 32 Bits zu sein; halb so groß wie der Typ double
, so überschreibt dies nur die untere Hälfte von 98.98
, die früher auf dem Stapel war. Die obere Hälfte von 98,98 ist noch auf dem Stapel.
Jetzt der dritte Aufruf an printf
liest eine double
aus dem Stapel. Die wichtigste Hälfte dessen, was es liest, kommt von der 98.98
, die früher auf dem Stapel war, und die weniger signifikante Hälfte kommt von der binären Darstellung von 98
; deshalb liegt das Ergebnis so nahe bei 98.98
. Da 98 eine so kleine Zahl ist, sind die höchstwertigen Bits 0, und wenn Sie die niedrigstwertige Hälfte von 98.98
auf Nullen setzen, erhalten Sie eine kleinere Zahl.
Wenn Zeile 3 eine Zahl verwendet, die mehr Bits auf 1 gesetzt hat, erhalten Sie ein Ergebnis, das mehr als 98.98
ist. Zum Beispiel hat die binäre Darstellung von -1 alle seine Bits auf 1 gesetzt, und Sie erhalten:
printf("line 2: %f\n", 98.98); # 98.98
printf("line 3: %f\n", -1); # 98.980042
Wenn der Compiler 64 Bit ints verwendet oder weitergegeben double
s mit dem wesentlichsten Teil zuerst, oder einen gebrauchten Registrieren Sie anstelle des Stapels, um Parameter zu übergeben, Sie würden sehr unterschiedliche Ergebnisse erhalten.
http://codepad.org/P6wolXsM –
@hbrock, der Compiler spielt keine Rolle. OP-Code verursacht undefiniertes Verhalten. Diese Frage ist ein Duplikat von Hunderten von Malen. –
weil ein int an printf übergeben wird, wenn es float erwartet, deshalb funktionierte es komisch. Aber mein Punkt ist, warum in der letzten Druckanweisung, anstatt einen Müllwert oder 0 zu drucken, es den Wert der 2. printf-Anweisung verwendet, und das wird was gedruckt. –