Verarbeitung von Multiplikationen



  • Wie wird denn ein Ausdruck, wie z.B.

    int h = a * 8;
    

    intern verarbeitet? Ist es das gleiche, wie wenn ich

    int h = a << 3;
    

    schreibe, oder hab ich beim zweiten Beispiel "performance-mäßig" einen Vorteil?



  • ist identisch.

    geht sogar soweit, daß er auch x*10 zu (x<<3)+(x<<1) macht, wenn er mag. aber vorher schaut er, welchen prozessor du als zielplatform beim compiler eingestellt hast und um der prozessor schneller plutimizieren kann als zwei shifts und ne addition.

    besonders bei divisionen lohnt es sich, zweierpotenzen zu nehmen, weil divisionen lahm sind.

    und unsigned-typen, wenigstend bei modulo-rechnungen, macht irgendwie weiger code, hab aber vergessen, warum. war was damit, daß % für negative zahlen komisch definiert ist und er deswegen beim ersetzen von & nach & er nachher noch gucken muß, ob der eingangswert keliner 0 war und gegebenenfalls noch ne kleinigkeit am ergebnis ändern.



  • bei einer anwendung habe ich mit 2 mutlipliziert, da mir gesagt wurde das ein guter Compiler so etwas in einen Shift umwandelt

    druch eine Messung habe ich allerdings festgestellt, das mein Compiler dumm ist



  • Vertexwahn schrieb:

    druch eine Messung habe ich allerdings festgestellt, das mein Compiler dumm ist

    mach mal vor dem messen die optimierungen des compilers an.



  • Was ein Compiler kann man sich doch anzeigen lassen, wenn man nicht fertig compiliert, sondern in des Assamble-Code.
    z.B.: gcc -S foo.c

    Außerdem ist es auch die Frage welche Optimierungsstärke du verwendest.



  • Toasterwilli schrieb:

    Wie wird denn ein Ausdruck, wie z.B.

    int h = a * 8;
    

    intern verarbeitet? Ist es das gleiche, wie wenn ich

    int h = a << 3;
    

    schreibe

    Nein, das erste ist definiert, das zweite nicht, wenn a ein negativer Wert ist. Die meisten Implementierungen werden in diesem Fall trotzdem bei beiden gleiche Ergebnisse liefern, weil dann arithmetisch geshiftet wird.

    Toasterwilli schrieb:

    oder hab ich beim zweiten Beispiel "performance-mäßig" einen Vorteil?

    Mach dir darüber keine Gedanken und verlass dich auf deinen Compiler. Wichtiger ist es, dass der Code das ausdrückt, was du machen willst. Wenn du also multiplizieren willst, dann tu das auch.



  • volkard schrieb:

    ist identisch.

    jaein. Bei Binärzahlen ja, aber die PCs arbeiten mit 2er Kompl. Darstellung und dann ist ein [lshift(a)] != [2*a] wenn a_{n-1} != a_{n-2} (für n=32, 64, usw)



  • supertux schrieb:

    volkard schrieb:

    ist identisch.

    jaein. Bei Binärzahlen ja, aber die PCs arbeiten mit 2er Kompl. Darstellung und dann ist ein [lshift(a)] != [2*a] wenn a_{n-1} != a_{n-2} (für n=32, 64, usw)

    geht das auch in klartext?
    und trenne bitte zwischen signed int und unsigned int, falls die unterschiedlich sind.


Anmelden zum Antworten