Frage

Meine Lösung: (Für jedes Bit des Eingangsblocks gibt es eine solche Linie)

*parity ^= (((x[0] >> 30) & 0x00000001) * 0xc3e0d69f);

Alle Typen sind uint32. Diese Zeile nimmt das zweite Bit des Eingangs X an, verschiebt es in die LSB und setzt alle anderen Bits auf Null. Anschließend wird die 32 -Bit -Parität mit der entsprechenden Paritätsabteilung für dieses Bit XARED.

Ich fand, dass diese Multiplikationslösung der schnellste Weg ist, um dieses bedingte XOR zu tun. Gibt es einen schnelleren Weg?

War es hilfreich?

Lösung

Ich verstehe nicht vollständig, welche Art von Parität Sie meinen, aber wenn diese Codezeile, die Sie wollen, können sie verbessert werden.

Allgemeine Regel: für x in {0, 1} x * N == -x & N

Dies, weil -x für 0 sind alle Bits zurückgesetzt und für 1 -1, in dem alle Bits eingestellt sind.

Daher kann die ursprüngliche Codezeile umgeschrieben werden wie:

*parity ^= (-((x[0] >> 30) & 0x00000001) & 0xc3e0d69f);

Was zwei Vorgänge in kürzerer Zeit berechnet als die Multiplikation bei vielen Mikroprozessoren, aber Sie sollten dies überprüfen.

Auch der Code kann das signierte Verschiebung rechts nutzen

*parity ^= (((int32_t)x[0] << 1 >> 31) & 0xc3e0d69f);

Die erste Schicht rShifts 30. Bit in 31., was Zeichenbit ist, und dann verlängern Sie das zweite Zeichen für alle anderen, wenn sich die meisten Maschinen direkt als Boden verändern (als Bodenx / 2N), somit in Bits mit Schildbit verschoben (abc...yz>>3 == aaaabc...yz).

Aber diese Tricks werden als angegeben als undefiniertes Verhalten im C Standard und so nicht tragbar. Verwenden Sie sie sorgfältig.

Andere Tipps

Siehe hier Für einige nette Hacks zur Berechnung der Parität eines Wortes, Byte usw.

Einige Prozessoren werden dies für Sie tun. Siehe x86 Paritätsflagge.

Wenn ich die Frage richtig verstehe, tun Sie es

for (i = 0; i < 32; i++)
    *parity ^= (((x[0] >> i) & 1) * SOME_CONST[i]); 

Wenn ja, ist es besser, Suchtische zu verwenden:

for (i = 0; i < 4; i++)
    *parity ^= PARITY_LUT[i][ (x[0] >> (i*8)) & 0xFF];

Es würde 256 KB kosten, wird aber viel schneller sein.

Die Paritätsberechnungsaufgabe entspricht der Zählung derjenigen. Auch als "Count -Set -Bits", "Bevölkerung Cont" oder einfach Popcount bezeichnet. Einige Prozessoren haben effiziente Anweisungen zur Berechnung (Popcnt, VCNT).

Ich werde empfehlen, das niedrigste Popcount zu verwenden.

Es kann durch Inline -Assembler oder mit Gebäuden zugreift: __builtin_popcount ()/ __popcnt ()/ std :: bitset :: count () für gcc/ vs/ c ++

Persönlich lieber ich diesen Job dem Compiler durch die Verwendung __builtin_parity ()

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top