I was trying to use this converted over from Bit Twiddling Hacks but it seems to fail when the first two bits are set. Clearly I've dunced something up but as far as my limited bit skills can take me I'm not sure what it is. It's supposed to count the number of bits in a 32 bit integer, which I assume could be the culprit, but I find it odd its only the first two bits that mess it up. They add 257 to the returned value or 514 if they are both set. The rest of the bits are counted fine.
Any master builders want to take a swing?
/// int popcnt(value) // any :: function; returns the number of bits set in value var v = argument0, c; v = v - ((v >> 1) & $55555555); v = (v & $33333333) + ((v >> 2) & $33333333); c = ((v + (v >> 4) & $F0F0F0F) * $1010101) >> 24; return c;
EDIT: I realized I'm an idiot, it isn't the first two values, it's 256 and 512. I assume this problem will be witnessed for bits beyond those numbers as well though I haven't tested anything higher. It properly counts the bits set in any number 255 or lower, must diagram the problem ...
So basically, as each bit rises, ie: (1 << x++), it returns 1 until bit 9 at which point it returns 257. Adding in a lower bit gives 258. Adding in a higher bit gives 514. So, 257 x 2. I'm guessing it's either a flaw in using this operation on a double, which while I don't fully understand the wizardry at work seems like it should be fine as long as your integer doesn't exceed 32 bits, or and OOO mistake or something like that.
EDIT 2: Well, it seems I was able to implement HAKMEM 169 and it does indeed work, at least for my purposes.
/// int popcnt(value) // any :: function; returns the number of bits set in value var v = argument0, c; c = v - ((v >> 1) & $DB6DB6DB) - ((v >> 2) & $49249249); return (c + (c >> 3) & $C71C71C7) % 63;
So yeah, if you need a hamming weight for a 32-bit number, there you go.
Edited by Hyomoto, 09 January 2016 - 12:04 AM.