Skip to content

Instantly share code, notes, and snippets.

@Redchards
Created September 8, 2015 09:39
Show Gist options
  • Save Redchards/dc72ba52cb36392f520f to your computer and use it in GitHub Desktop.
Save Redchards/dc72ba52cb36392f520f to your computer and use it in GitHub Desktop.
I have a bad tendency to not write things. So I tend to forget some nice tricks. I will use this gist to list some of them as I remember/learn them
We will assume for all the following examples that x > 0 (IMPORTANT !)
This little formula will determine if the number is power of two :
(x & -x) == x
How does it works ?
First, let's try to formulate what it means in english :
The only bits that x and -x have set to 1 in common, are the bits
set to 1 in x.
In fact, it's based on a simple observation. Let examine the number 4 :
4 = 00000100b
-4 = ~00000100b + 1b
= 11111011b + 1b
= 11111100b
thus : 4 & -4 = 00000100b & 11111100b = 00000100b = 4
This is not possible if the number is not a power of two. Indeed, if the power is
not a power of two, then more than one bit in the number is equal to one. Thus, the
negative representation of this number could not have all the 1 bit in the
positive number set to 1 (because the two's complement only add 1b)
For example, take the number 5:
5 = 00000101b
-5 = ~00000101b + 1b
= 11111010b + 1b
= 11111011b
We can also use x & (x-1) == 0.
There's a nice trick (that modern compilers do automatically) to check if a number is odd or even.
The canonical way of checking if a number x is even for example, is :
x % 2 == 0
But we can use the fact that if x is even, the the LSB is 0. Of course, the LSB always represent 1,
and if it is 1, then the number can not be even. To understand it a bit better, it's worth to consider
mathematical representation of even and odd numbers :
For all natural numbers n, then 2n is even, and 2n + 1 is odd.
So, we just need to apply this fact to our problem, and we got that x is even if and only if :
x & 1 == 0
Similarly, to check if a number is odd :
x & 1 != 0
This trick is usually unecessary when working with modern compiler, but when dealing with assembly,
or other things like this, it could be useful.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment