Take the 2-minute tour ×
Programmers Stack Exchange is a question and answer site for professional programmers interested in conceptual questions about software development. It's 100% free, no registration required.

I've seen others use Bitwise-OR to combine flags before:

#define RUN 0x01
#define JUMP 0x02
#define SHOOT 0x04

const byte madPerson = RUN | JUMP | SHOOT;

That's also the way I do it.

But I've also seen some (not as many) combine flags using addition:

#define RUN 0x01
#define JUMP 0x02
#define SHOOT 0x04

const byte madPerson = RUN + JUMP + SHOOT;

Which one is more "readable"? (Which one do you think more people will recognize?) What is the "standard" way to do it? Which one do you prefer?

share|improve this question
    
This is a SO question. Consider using something like 1<<0, 1<<1, 1<<2, and so on. When you have many flags, it becomes more readable, more maintainable, less error-prone. For instance, if you are packing all 64 bits of a 64 bit int, you really want to avoid typos :) How you represent 1 is also important. For a 64 bit integer in VS2010 I think it is 1UI64, or something like that. Using a wrong type might bite you. –  Job Dec 5 '10 at 14:08
2  
@Job: Not a StackOverflow question, because it's asking about readability, recognizability, preferences and best practices. No single objective answer for it; it belongs here. –  Macneil Dec 26 '10 at 16:32
add comment

2 Answers

up vote 22 down vote accepted

Bitwise-OR.

Addition is dangerous.

Consider an example where a bandit is a person, and an angry bandit is a bandit that speaks and shoots. Later, you decide all bandits should shoot, but you've forgotten about the angry bandit definition and don't remove its shooting flag.

#define PERSON 1 << 0
#define SPEAKS 1 << 1
#define SHOOTS 1 << 2
#define INVINCIBLE 1 << 3
const byte bandit = PERSON | SHOOTS;                    // 00000101
const byte angryBandit_add = bandit + SPEAKS + SHOOTS;  // 00001011 error
const byte angryBandit_or = bandit | SPEAKS | SHOOTS;   // 00000111 ok

If you used angryBandit_add your game would now have the perplexing logic error of having angry bandits that can't shoot or be killed.

If you used angryBandit_or the worst you'd have is a redundant | SHOOTS.

For similar reasons, bitwise NOT is safer than subtraction for removing flags.

share|improve this answer
6  
+1 for "Addition is dangerous." –  tcrosley Dec 5 '10 at 16:00
add comment

bitwise-OR conveys the intent more clearly

also, bitwise-OR should be more efficient

share|improve this answer
    
+1 indeed I also think that OR makes it more clear that those are flags, but concerning the efficiency there are languages where bitwise operations are slow, e.g. JavaScript all Numbers are 64 floats bitwise operators need to do implicit conversion on those. –  Ivo Wetzel Dec 5 '10 at 6:17
1  
Given the OP's example, I don't think one line of ORs or addition is going to adversely impact the execution speed of a program. –  the Tin Man Dec 5 '10 at 7:33
1  
@Greg: especially since the calculation in that example will be done at compile time. :-) –  Carson63000 Dec 5 '10 at 7:43
2  
+1 for "conveying intent", -1 for "more efficient" –  Paul R Dec 5 '10 at 10:40
1  
"should" is a very big word in this business. While it is highly unlikely that you will encounter this issue today, I have very clear memories of working on a processor that did not have a bitwise-OR instruction. You could bitwise-AND in one instructn, and you could bitwise-XOR in one instruction, but bitwise-OR took two: an immediate bitwise-AND to turn the bit off, and an immediate bitwise-XOR to complement the newly-cleared bit, which of course set it. –  John R. Strohm Dec 5 '10 at 14:38
show 2 more comments

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.