Using bitwise operators with Actionscript to create arguments flags

Among all books I bought (including Java books), I haven’t one which explain in depth and in a clear manner what bitwise operators are and how to use them. Almost all books has at least a page about the argument but none is able to give an exhaustive explanation. So, after searching the net, I found an extreme useful article by Joseph Farrell on gamedev.net (direct link: http://www.gamedev.net/reference/articles/article1563.asp), which explains bitwise operators in C starting from an introduction to Numbers and number system. The article is valid to Actionscript, Java and other languages too. I started to try to understand bitwise operators, after looked to Flex’s Alert class, which can accept several options (different buttons) as an unique argument (flags). This can be accomplished by using the bitwise OR operator |  (a pipe), which “joins” together different constants:

Alert.show("Alert message", "Alert title", Alert.OK | Alert.NO | Alert.CANCEL);

The code above generates an alert with 3 buttons (ok, no and cancel), but how it works exactly? Well, I don’t want to rewrite the article I read, but I would like to synthesize it and focus on an Actionscript usage, in order to give the basic information required to create custom classes which will accept multiple parameters an unique argument. So… what Alert.OK, Alert.NO and so on are? They are basically numbers (uint), and the result of the bitwise or operator still returns an integer, so the Alert class will receives a number as the third argument. The | operator, in practice produces a “binary sum” of the given numbers. A good way I figured out to understand what is going on when using that operator is to trace the binary representation of every number passed and then the result after the bitwise operation. To convert a “normal number” (base 10) into a binary one (base 2… only 1 or 0 sequence), we can use the toString() method by passing 2 as the radix argument:

var myNumber:uint = 3560;
trace(myNumber.toString(2));

The code above will trace: 110111101000.

So, let’s create a dummy class to do some tests:

package {

    public class BitwiseTest {

        public static const FLAG_1:uint = 1;
        public static const FLAG_2:uint = 2;
        public static const FLAG_3:uint = 4;
        public static const FLAG_4:uint = 8;
        public static const FLAG_5:uint = 16;
        public static const FLAG_6:uint = 32;

        public function BitwiseTest() {

            trace("BitwiseTest.FLAG_1: " + BitwiseTest.FLAG_1.toString(2));
            trace("BitwiseTest.FLAG_3: " + BitwiseTest.FLAG_3.toString(2));
            trace("BitwiseTest.FLAG_5: " + BitwiseTest.FLAG_5.toString(2));
            trace("BitwiseTest.FLAG_6: " + BitwiseTest.FLAG_6.toString(2));

            this.test(BitwiseTest.FLAG_1 | BitwiseTest.FLAG_3 | BitwiseTest.FLAG_5 | BitwiseTest.FLAG_6);

        }

        private function test(flags:uint):void {

            trace("flags: " + flags.toString(2));

        }

    }

}

The trace output will be:

BitwiseTest.FLAG_1: 1
BitwiseTest.FLAG_3: 100
BitwiseTest.FLAG_5: 10000
BitwiseTest.FLAG_6: 100000
flags: 110101

To check for a specific flag’s presence inside flags argument, we can use the bitwise “and” operator (&):

if ((flags & BitwiseTest.FLAG_1) > 0) {

    trace("BitwiseTest.FLAG_1 passed - (" + String(flags & BitwiseTest.FLAG_1) + ")");

}

By using the & operator on flags it will returns the flag’s value if passed to the method and 0 otherwise. By updating the test method in this manner:

private function test(flags:uint):void {

    trace("flags: " + flags.toString(2));

    if ((flags & BitwiseTest.FLAG_1) > 0) {

        trace("BitwiseTest.FLAG_1 passed - (" + String(flags & BitwiseTest.FLAG_1) + ")");

    }

    if ((flags & BitwiseTest.FLAG_2) > 0) {

        trace("BitwiseTest.FLAG_2 passed - (" + String(flags & BitwiseTest.FLAG_2) + ")");

    }

    if ((flags & BitwiseTest.FLAG_3) > 0) {

        trace("BitwiseTest.FLAG_3 passed - (" + String(flags & BitwiseTest.FLAG_3) + ")");

    }

    if ((flags & BitwiseTest.FLAG_4) > 0) {

        trace("BitwiseTest.FLAG_4 passed - (" + String(flags & BitwiseTest.FLAG_4) + ")");

    }

    if ((flags & BitwiseTest.FLAG_5) > 0) {

        trace("BitwiseTest.FLAG_5 passed - (" + String(flags & BitwiseTest.FLAG_5) + ")");

    }

    if ((flags & BitwiseTest.FLAG_6) > 0) {

        trace("BitwiseTest.FLAG_6 passed - (" + String(flags & BitwiseTest.FLAG_6) + ")");

    }		

}

We will obtain this output:

BitwiseTest.FLAG_1: 1
BitwiseTest.FLAG_3: 100
BitwiseTest.FLAG_5: 10000
BitwiseTest.FLAG_6: 100000
flags: 110101
BitwiseTest.FLAG_1 passed - (1)
BitwiseTest.FLAG_3 passed - (4)
BitwiseTest.FLAG_5 passed - (16)
BitwiseTest.FLAG_6 passed - (32)

We have successfully “intercepted” what flags has been passed to the method.
Is important to know that flag’s values can’t be progressive numbers, but they must be multiples of 2, otherwise when using the bitwise “or” operator we will obtain a “ones overlap” resulting in an entity we won’t be able to properly manage. If we replace the flags values used in the previous example in this way:

public static const FLAG_1:uint = 1;
public static const FLAG_2:uint = 2;
public static const FLAG_3:uint = 3;
public static const FLAG_4:uint = 4;
public static const FLAG_5:uint = 5;
public static const FLAG_6:uint = 6;

We will get the following output:

BitwiseTest.FLAG_1: 1
BitwiseTest.FLAG_3: 11
BitwiseTest.FLAG_5: 101
BitwiseTest.FLAG_6: 110
flags: 111
BitwiseTest.FLAG_1 passed - (1)
BitwiseTest.FLAG_2 passed - (2)
BitwiseTest.FLAG_3 passed - (3)
BitwiseTest.FLAG_4 passed - (4)
BitwiseTest.FLAG_5 passed - (5)
BitwiseTest.FLAG_6 passed - (6)

As we can see our test method is unable to understand what flags it has received due to “ones overlap” (looks at te first 5 lines).

In conclusion… using bitwise operators for flags are pretty simple, however bitwise operators can do much more but understanding the real power of these operators and how to properly use them is not so easy (at least to me :-))

  • An excellent book on bitwise operators is “Hacker’s Delight” by Henry S. Warren, Jr. It gives extensive coverage of the old school techniques — a dying art.