Was ist der Unterschied zwischen
float f = (float) 99.32 ;
und
float f = 99.32f ;
Beide wurden erfolgreich kompiliert und ausgeführt.
Was ist der Unterschied zwischen
float f = (float) 99.32 ;
und
float f = 99.32f ;
Beide wurden erfolgreich kompiliert und ausgeführt.
Magisch
float f = 99.32f ;
Das ist ein float
Literal, was bedeutet, dass eine Float-Variable mit a zugewiesen wird float
Wert direkt.
float f = (float) 99.32 ;
Das ist ein float
Variable, der a zugewiesen wird double
Wert, auf den gecastet wird float
vor der Zuweisung.
Würde der Compiler dies optimieren? (im Gussfall)
– Austi01101110
16. Oktober 2015 um 7:12 Uhr
nein, 99.32
ist ein Fließkommaliteral, das den Typ hat double
.
– mch
16. Oktober 2015 um 8:14 Uhr
nein, 99.32
ist ein double
, nicht implizit darauf gecastet. Dies wird als “Gleitkommaliteraltyp” bezeichnet double
“. 99.32f
ist ein float
und nicht dazu gecastet. Dies wird als “Gleitkommaliteraltyp” bezeichnet float
“. Es gibt keine Besetzung bei float f = 99.32f;
oder double d = 99.32;
.
– mch
16. Oktober 2015 um 8:23 Uhr
Gibt es einen Wertunterschied zwischen den beiden?
– John Dvorak
16. Oktober 2015 um 13:53 Uhr
@JanDvorak: Selten und in diesem Fall wahrscheinlich nicht. (Float) 99,32 ist die reelle Zahl 99,32, gerundet auf die nächste verfügbare Double-Zahl, gerundet auf die nächste verfügbare Float-Zahl. 99,32f ist die reelle Zahl 99,32, gerundet auf die nächste Gleitkommazahl. Sei x eine Zahl, die genau in der Mitte zwischen zwei benachbarten Gleitkommazahlen liegt. Seien d und d’ zwei Dezimalzahlen, die nur ein winziges bisschen größer/kleiner als x sind. Dann würde das .f-Suffix auf-/abgerundet werden, aber das Runden auf das Doppelte könnte in beiden Fällen das Ergebnis x ergeben, und das Casting auf float würde entweder d oder d’ in die falsche Richtung runden.
– gnasher729
16. Oktober 2015 um 22:41 Uhr
Himmel König
Der Unterschied kann wegoptimiert werden, aber im ersten Fall haben Sie ein doppeltes Literal, das in einen Float umgewandelt wird, während Sie im zweiten Fall ein Float-Literal haben.
Wenn Sie nicht wegoptimiert sind, erhalten Sie im zweiten Beispiel eine Typumwandlung im Code.
Es gibt jedoch Ausnahmefälle, in denen das Ergebnis (je nach Rundungsmodus) geringfügig abweichen kann. Wenn Ihre Zahl nicht genau dargestellt werden kann, wird im ersten Fall zweimal gerundet – zuerst, wenn Sie die Dezimaldarstellung auf ein Double runden, und dann, wenn Sie diese auf einen Float runden, während Sie im ersten Fall die Dezimaldarstellung direkt runden zu einem Schwimmer.
Da ein ULP mit einfacher Genauigkeit so viel größer ist als ein ULP mit doppelter Genauigkeit, kann ich kaum glauben, dass die doppelte Rundung einen signifikanten Effekt haben könnte.
– Kevin
16. Oktober 2015 um 13:31 Uhr
@Kevin Es hätte eine Wirkung von bis zu eins schweben ULP-Unterschied.
– John Dvorak
16. Oktober 2015 um 13:54 Uhr
Ich vermute, dass es einen Eckfall gibt, habe ihn aber nicht gefunden.
– chux – Wiedereinsetzung von Monica
16. Oktober 2015 um 15:18 Uhr
0,50000008940696713 ergibt ein anderes Ergebnis: mit Rundung erhält man 0x1.000004p-1
während Sie mit Suffix erhalten 0x1.000002p-1
(sehen ideone.com/EV3QeG). Siehe auch en.wikipedia.org/wiki/Rounding#Double_rounding
– Matthias M.
16. Oktober 2015 um 17:59 Uhr
Genauer gesagt, die letzten beiden Ziffern von 11-21 ergeben alle 0x1.000003p-1
als doppelt (und daher 0x1.000004p-1
wenn doppelt gerundet auf Float) und die letzten beiden Ziffern von 11-16 (ungefähr die Hälfte dieses Bereichs) ergeben 0x1.000002p-1
. Der Wertebereich, über den dies auftreten kann (für jeden Fall vermutlich mit einem Abstand von einem ULP-Float), ist ungefähr die Hälfte eines doppelten ULP breit und ergibt in jedem Fall einen “Fehler” von einem halben ULP-Float, wenn gerundet wird nach oben oder unten, da die realen Werte ungefähr in der Mitte zwischen zwei Float-Werten liegen.
– Random832
16. Oktober 2015 um 18:36 Uhr
Im ersten Fall ohne Besetzung 99.32
wird als Double und nicht als Float interpretiert.
Ein doppeltes Literal wird gecastet, um zu schweben.
Im zweiten Fall haben Sie ein Suffix f
um sicherzustellen, dass der Compiler behandelt 99.32
als Schwimmer.
code_dredd
In der Schlange float f = (float) 99.32;
das wörtliche 99.32
wird erstellt als double
Typ standardmäßig und wird dann in a umgewandelt float
.
In der Schlange float f = 99.32f ;
das Literal wird als a erstellt float
Typ aufgrund des Nachgestellten f
in 99.32f
und es ist kein Typcasting erforderlich.
Letzteres wäre analog zum Schreiben double f = 99.32;
wie du hättest double
Typ direkt einer Variablen eines übereinstimmenden Typs zugewiesen wird.
101010
Fließkommaliterale ohne Suffix sind standardmäßig double
Typ.
So heißt es float f = (float) 99.32;
du wirfst zuerst ausdrücklich wörtlich 99.32
was vom Typ ist double
zu einem float
und dann der Variablen zuweisen f
.
Angeben float f = 99.32;
macht das gleiche, aber in diesem Fall die Die Konvertierung zwischen den Typen erfolgt implizit.
Wenn Sie eine implizite Konvertierung vermeiden möchten, sollten Sie die verwenden f
Suffix, um Ihr Literal zu definieren (d. h. float f = 99.32f;
)
nein, sie sind nicht dasselbe, ohne die f
Suffix ist das Ergebnis manchmal falsch
– phuklv
17. April um 10:32 Uhr
Evdzhan Mustafa
Der Unterschied besteht darin, dass das wörtliche 99.32
ist vom Typ double, während das Literal 99.32f
ist vom Typ Float.
Die erste Anweisung weist das Float-Literal einer Float-Variablen zu. Nichts Besonderes.
Die zweite Anweisung wandelt ein Double-Literal in einen Float um und weist das Ergebnis einer Float-Variablen zu.
Standardmäßig können Sie einer Float-Variablen ein Double-Literal zuweisen, ohne es explizit selbst zu casten. In diesem Fall erfolgt eine implizite Umwandlung. Z.B :
float f = 99.32;
Sie können sogar Folgendes tun:
float f = (double) 10.5f;
und die rechte Seite wird immer noch implizit in einen Float umgewandelt.
Bitte beachten Sie, dass die meisten modernen Compiler diese wegoptimieren, sodass die Darstellung von Gleitkommazahlen normalerweise eine Frage des Stils und der Präferenz ist. Sei einfach konsequent.
nein, sie sind nicht dasselbe, ohne die f
Suffix ist das Ergebnis manchmal falsch
– phuklv
17. April um 10:32 Uhr
Der erste leidet darunter doppelter Rundungsfehler, was nicht gut ist, da das Ergebnis möglicherweise nicht den gewünschten Wert hat. Der zweite erzeugt einen korrekt gerundeten Float-Wert en.wikipedia.org/wiki/Rounding#Double_rounding
– phuklv
16. Oktober 2015 um 8:15 Uhr
Dieser Link verwendet eine viel zu lange Darstellung seiner Beispielnummer. “0.50000008940696713” ist ausreichend.
– Random832
16. Oktober 2015 um 16:13 Uhr
@LưuVĩnhPhúc: Ich gehe davon aus, dass eine genaue Dezimaldarstellung eines Werts auf halbem Weg zwischen zwei benachbarten Doppelwerten verwendet wurde, obwohl ich vorschlagen würde, dass das Hinzufügen einer großen Ganzzahl zum Wert präzise Dezimaldarstellungen viel kürzer und offensichtlicher machen würde.
– Superkatze
16. Oktober 2015 um 19:09 Uhr
1. Meinen Sie speziell für diese Dezimalzeichenfolge oder für eine beliebige? 2. Was bedeutet „erfolgreich“? “Den gleichen Wert zurückgegeben”? (Testen sie als gleich? Haben Sie das untersucht gesamte Darstellung?)
– Philippie
21. Oktober 2015 um 8:38 Uhr