performance - Is BitArray faster in C# for getting a bit value than a simple conjuction with bitwise shift? -
1). var bitvalue = (bytevalue & (1 << bitnumber)) != 0;
2). using system.collections.bitarray
get( bitnumber ) method
- what faster?
- in situations .net projects bitarray more useful simple conjunction bitwise shift?
bitarray
going able handle arbitrary number of boolean values, whereas byte
hold 8, int
32, etc. going biggest difference between two.
also, bitarray
implements ienumerable
, integral type not. depends on requirements of project; if need ienumerable
or array-like interface, go bitarray
.
i use bool[]
on either solution, because more explicit in what kind of data you're keeping track of. t
bitarray
or bitfield
use approximately 1/8th space of bool[]
because "pack" 8 boolean values single byte, whereas bool
take whole 8-bit byte. space advantage of using bitfield or bitarray
isn't going matter though until being storing lots of bools
. (the math left reader :-))
benchmark
results: primitive test environment, appears bitarray
bit faster, on same order of magnitude doing integral type. tested bool[]
, unsurprisingly fastest. accessing single bytes in memory going less complex accessing individual bits in different bytes.
testing 10000000 operations: uint32 bitfield took 808 ms. bitarray (32) took 574 ms. list<bool>(32) took 436 ms.
code:
class program { static void main(string[] args) { random r = new random(); r.next(1000); const int n = 10000000; console.writeline("testing {0} operations:", n); console.writeline(" uint32 bitfield took {0} ms.", testbitfield(r, n)); console.writeline(" bitarray (32) took {0} ms.", testbitarray(r, n)); console.writeline(" list<bool>(32) took {0} ms.", testboolarray(r, n)); console.read(); } static long testbitfield(random r, int n) { uint32 bitfield = 0; var sw = stopwatch.startnew(); (int = 0; < n; i++) { setbit(ref bitfield, r.next(32), true); bool b = getbit(bitfield, r.next(32)); setbit(ref bitfield, r.next(32), b); } sw.stop(); return sw.elapsedmilliseconds; } static bool getbit(uint32 x, int bitnum) { if (bitnum < 0 || bitnum > 31) throw new argumentoutofrangeexception("invalid bit number"); return (x & (1 << bitnum)) != 0; } static void setbit(ref uint32 x, int bitnum, bool val) { if (bitnum < 0 || bitnum > 31) throw new argumentoutofrangeexception("invalid bit number"); if (val) x |= (uint32)(1 << bitnum); else x &= ~(uint32)(1 << bitnum); } static long testbitarray(random r, int n) { bitarray b = new bitarray(32, false); // 40 bytes var sw = stopwatch.startnew(); (int = 0; < n; i++) { b.set(r.next(32), true); bool v = b.get(r.next(32)); b.set(r.next(32), v); } sw.stop(); return sw.elapsedmilliseconds; } static long testboolarray(random r, int n) { bool[] ba = new bool[32]; var sw = stopwatch.startnew(); (int = 0; < n; i++) { ba[r.next(32)] = true; bool v = ba[r.next(32)]; ba[r.next(32)] = v; } sw.stop(); return sw.elapsedmilliseconds; } }
Comments
Post a Comment