Warum optimiert GCC nicht a * a * a * a * a zu (a * a * a) * (a * a * a)?

Ich optimiere eine wissenschaftliche Anwendung numerisch. Eine Sache, die mir aufgefallen ist, ist, dass GCC den Anruf optimieren wirdpow(a,2) durch Kompilieren ina*a, aber der Anrufpow(a,6) ist nicht optimiert und ruft die Bibliotheksfunktion aufpow, was die Leistung stark verlangsamt. (Im Gegensatz,Intel C ++ Compiler, ausführbaresicc, beseitigt den Bibliotheksaufruf fürpow(a,6).)

Was ich neugierig bin ist, dass, wenn ich @ ersetpow(a,6) mita*a*a*a*a*a using GCC 4.5.1 und Optionen "-O3 -lm -funroll-loops -msse4 ", verwendet es 5mulsd Anweisungen:

movapd  %xmm14, %xmm13
mulsd   %xmm14, %xmm13
mulsd   %xmm14, %xmm13
mulsd   %xmm14, %xmm13
mulsd   %xmm14, %xmm13
mulsd   %xmm14, %xmm13

während wenn ich schreibe(a*a*a)*(a*a*a), es wird @ produzier

movapd  %xmm14, %xmm13
mulsd   %xmm14, %xmm13
mulsd   %xmm14, %xmm13
mulsd   %xmm13, %xmm13

, wodurch die Anzahl der Multiplikationsbefehle auf 3 reduziert wird.icc hat ein ähnliches Verhalten.

Warum erkennen Compiler diesen Optimierungstrick nicht?

Antworten auf die Frage(24)

Ihre Antwort auf die Frage