dieser druckt 100:
%Vor%und dieser druckt 99:
%Vor%warum?
Was passiert, ist, dass Sie eine C-Implementierung haben, deren Standardbibliothek eine Implementierung von pow
mit sehr geringer Qualität hat, die ungenaue Ergebnisse liefert, selbst wenn das genaue Ergebnis im Typ darstellbar ist ( double
). Der Aufruf von pow(10,2)
scheint den Wert direkt unter 100.0
zu erzeugen, was, wenn er auf eine Ganzzahl gerundet wird, 99 ergibt. Der Grund, warum Sie dies nicht sehen, wenn die Argumente konstant sind, ist, dass der Compiler sich die Freiheit zur Optimierung genommen hat aus dem Aufruf all zusammen und ersetzen sie durch eine Konstante 100 bei compiletime.
Wenn Sie beabsichtigen, ganzzahlige Potenzen zu verwenden, verwenden Sie nicht die Funktion pow
. Schreibe eine richtige ganzzahlige Potenzfunktion, oder wenn der Exponent bekannt ist, schreibe einfach die Multiplikation direkt aus.
Im ersten Fall vermute ich, dass der Compiler den Wert auf 10*10
optimiert hat, ohne tatsächlich pow
aufzurufen (Compiler tun dies tatsächlich). Im zweiten Fall sieht es so aus, als ob Sie einen Gleitkomma-Rundungsfehler haben. Das Ergebnis ist fast 100, aber nicht ganz, und die implizite Umwandlung in int
schneidet es ab.
Die Funktion pow
funktioniert auf double
, nicht auf int
.
Im Allgemeinen (aber nicht immer), wenn Sie doubles in Integer konvertieren, rufen Sie round()
auf. ZB:
Wenn Ihre C-Bibliothek dies nicht hat, können Sie emulieren:
%Vor% pow
gibt double
zurück, und wenn das Ergebnis nicht genau 100
ist, aber etwas weniger, als es beim Konvertieren in eine int
abgeschnitten wird, erhalten Sie das 99
Ergebnis, das Sie sehen. Es wäre interessant zu sehen, wie die Ergebnisse für eine double
Variable und %f
Format aussehen.
Der Grund, warum Sie es nicht sehen werden, wenn Sie Literale verwenden, ist das konstante Falten , das den Aufruf verursachen wird pow
wird optimiert und durch eine Konstante ersetzt. Wir können die Version sehen, die Konstanten verwendet, wenn wir die Assembly erzeugen, kein Aufruf von pow
gemacht wird, sondern nur das Endergebnis 100
( siehe leben ):
während die Version der zweiten Version tatsächlich pow
aufruft ( siehe live ):
Tags und Links c floating-point pow