Optimierung von sqrtf
-
Hi ich hab schon wieder ein Problemchen
Und zwar hab ich mir mal angeschaut wie das mit der
Wurzelberechnung implementiert ist
Das habe ich gefunden für floatinline float sqrtf(float _X) {return ((float)sqrt((double)_X)); }Quelle: math.h
Gut. Jetzt frag ich mich ob das gecaste und die funktion, die die eigentliche Wurzel berechnen vieleicht noch optimiert werden können.
Dabei bin ich auf eine Funktion gestoßen, die ich gern noch weiter optimieren würde, ich weis aber nicht so richtig wo ich anfangen soll.
inline float sqrtFast(float r) { if(r == 0.f) return 0.0f; r = (r<0 ? -r : r); Value = r; halfValue = 0.5f*r; ptr = (unsigned long*)&r; *ptr=(0xbe6f0000-*ptr)>>1; temp1Wurzel = r; temp1Wurzel *= 1.5f-temp1Wurzel*temp1Wurzel*halfValue; temp1Wurzel *= 1.5f-temp1Wurzel*temp1Wurzel*halfValue; temp1Wurzel *= 1.5f-temp1Wurzel*temp1Wurzel*halfValue; temp1Wurzel *= 1.5f-temp1Wurzel*temp1Wurzel*halfValue; temp1Wurzel *= 1.5f-temp1Wurzel*temp1Wurzel*halfValue; return Value*temp1Wurzel; }Kann das mal jemand optimieren, aber bitte KEIN ASSEMBLER.
Es wäre echt nett, und ich wäre echt froh, wenn sich von auch mal jemand ne Minute Zeit nehmen würde.
-
http://www.azillionmonkeys.com/qed/sqroot.html

.............
.............
.............
.............
.............
.............
.............
.............
.............
.............
.............
.............
.............
.............
.............
.............
.............
.............
.............
-
Danke, soweit war ich auch schon

-
OTTO schrieb:
Danke, soweit war ich auch schon
perfekt! wozu dann noch die frage hier?

-
Meiner Meinung nach versteh ich unter optimierung folgendes
"Optimierung = Beschleunigung"Beispielsweise bin ich mir nicht ganz sicher ob ich das wirklich 5mal brauche
temp1Wurzel *= 1.5f-temp1Wurzel*temp1Wurzel*halfValue;Sowas versteh ich unter Code-Optimierung
Ach ja:
Value ist float
HalfValue ist float
ptr ist (unsigned int
Fällt jemandem noch was ein wie der Code schneller wird oder antworten mir nur Wurzeksepp etc?
Ich bin für jede brauchbare Antwort dankbar
-
Meiner Meinung nach versteh ich unter optimierung folgendes
"Optimierung = Beschleunigung"
Sowas versteh ich unter Code-OptimierungROFL! Das tut aber nicht jeder und das ist sogar Fakt.
Schreib dir das ganze mal auf einen Zettel auf und vereinfache bzw. hebe hervor. Besonders die lustigen templWurzel Multiplikationen. Da is noch einiges drin.
-
Also ich habs schon soweit
inline float GTSqrt(float r) { if(r == 0.0f) return 0.0f; r = (r<0 ? -r : r); float Value = r; float halfValue=0.5F*r; unsigned long *ptr = (unsigned long*)&r; *ptr=(0xbe6f0000-*ptr)>>1; float temp1Wurzel = r; temp1Wurzel *= 1.5f-temp1Wurzel*temp1Wurzel*halfValue; temp1Wurzel *= 1.5f-temp1Wurzel*temp1Wurzel*halfValue; return Value*temp1Wurzel; }Kanns das mal jemand BITTE noch weiter optimieren, ich weis nehmlich nicht wo ich da noch was machen soll. Bitte...
-
du kannst noch eine zeile entfernen von dieser tmpWurzel sache, nur wird dann die genauigkeit immer geringer,
-
Wie oben schon geschehen, reichen zwei Iterationen i.d.R. schon aus... Hier aber eine verkürzte Variante aus dem QuakeIII Quellcode:
float Q_rsqrt( float number ){ long i; float x2, y; const float threehalfs = 1.5F; x2 = number * 0.5F; y = number; i = * ( long * ) &y; // evil floating point bit level hacking i = 0x5f3759df - ( i >> 1 ); // what the fuck? y = * ( float * ) &i; y = y * ( threehalfs - ( x2 * y * y ) ); // 1st iteration // y = y * ( threehalfs - ( x2 * y * y ) ); // 2nd iteration, this can be removed return y; }
-
Danke!
Aber der Code ist falsch
ich hab ihn überarbeitet und jetzt klappts wirklichfloat Q_rsqrt( float number ){ long i; float x2, y; const float threehalfs = 1.5F; x2 = number * 0.5F; y = number; i = * ( long * ) &y; // evil floating point bit level hacking i = 0x5f3759df - ( i >> 1 ); // what the love? y = * ( float * ) &i; y = y * ( threehalfs - ( x2 * y * y ) ); // 1st iteration // y = y * ( threehalfs - ( x2 * y * y ) ); // 2nd iteration, this can be removed return y*number; }Kleines Problemchen wäre da nur noch dass beispielsweise Wurzel von 2 nur die ersten 2 stellen richtig sind, bei meiner sind es ganze 6 Stellen sind, schon schade, aber mit 2 Iterationen klappts
Aber kriegt man die noch schneller?
-
Wiegesagt, du kannst die Genauigkeit mit beliebig vielen Iterationen hochschrauben, es war ja auch nur ein Denkanstoß. Ich denke, was schnelleres wirst du nicht in die Hände bekommen...
-
Wozu das ganze? Die Hardwareimplementierungen von sqrt auf aktuellen Architekturen (zB x86) sind schneller als jede manuelle Version, zumindest bei vergleichbarer Genauigkeit.