Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Bitwise OR of constants

While reading some documentation here, I came across this:

unsigned unitFlags = NSYearCalendarUnit | NSMonthCalendarUnit |  NSDayCalendarUnit;

I have no idea how this works. I read up on the bitwise operators in C, but I do not understand how you can fit three (or more!) constants inside one int and later being able to somehow extract them back from the int? Digging further down the documentation, I also found this, which is probably related:

typedef enum {
   kCFCalendarUnitEra = (1 << 1),
   kCFCalendarUnitYear = (1 << 2),
   kCFCalendarUnitMonth = (1 << 3),
   kCFCalendarUnitDay = (1 << 4),
   kCFCalendarUnitHour = (1 << 5),
   kCFCalendarUnitMinute = (1 << 6),
   kCFCalendarUnitSecond = (1 << 7),
   kCFCalendarUnitWeek = (1 << 8),
   kCFCalendarUnitWeekday = (1 << 9),
   kCFCalendarUnitWeekdayOrdinal = (1 << 10),
} CFCalendarUnit;

How do the (1 << 3) statements / variables work? I'm sorry if this is trivial, but could someone please enlighten me by either explaining or maybe posting a link to a good explanation?

like image 586
ryyst Avatar asked May 29 '10 20:05

ryyst


2 Answers

Basically, the constants are represented just by one bit, so if you have a 32 bit integer, you can fit 32 constants in it. Your constants have to be powers of two, so they take only one "set" bit to represent.

For example:

#define CONSTANT_1 0x01 // 0001 in binary
#define CONSTANT_2 0x02 // 0010 in binary
#define CONSTANT_3 0x04 // 0100 in binary

then you can do

int options = CONSTANT_1 | CONSTANT_3; // will have 0101 in binary.

As you can see, each bit represents that particular constant. So you can binary AND in your code and test for the presence of each constant, like:

if (options & CONSTANT_3)
{
    // CONSTANT_3 is set
}

I recommend you to read about binary operations (they work like LOGICAL operators, but at the bit level), if you grok this stuff, it will make you a bit better of a programmer.

Cheers.

like image 133
Francisco Soto Avatar answered Sep 23 '22 15:09

Francisco Soto


If you look at a number in binary, each digit is either on (1) or off (0).

You can use bitwise operators to set or interrogate the individual bits efficiently to see if they are set or not.

Take the 8 bit value 156. In binary this is 10011100.

The set bits correspond to bits 7,4,3, and 2 (values 128, 16, 8, 4). You can compute these values with 1 << (position) rather easily. So, 1 << 7 = 128.

like image 34
Joe Avatar answered Sep 21 '22 15:09

Joe