[Tutor] Strange operator

Danny Yoo dyoo at hkn.eecs.berkeley.edu
Fri Nov 5 01:25:15 CET 2004



On Thu, 4 Nov 2004, Chad Crabtree wrote:

> I was perusing the wax sourcecode and ran accross this
>         style |= styles.frame(kwargs)
>         style |= styles.window(kwargs)
>
> the pipe-equal operator is something I've never seen this before,
> after
> a little searching I found this
>
> Bitwise OR              *|*        1 if lhs bit OR rhs bit = 1
>
> http://www.mhuffman.com/notes/language/py_intro.htm#LOGIC
>
> which confuses me even more because I'm not sure how this is useful.
> Could someone please explain this?



Hi Chad,


Underneath the surface, integers in Python are stored as a series of bits.
For example, the following sequence of bits:

    100010100100

can stand for the integer 2212:

###
>>> int('100010100100', 2)
2212
###


So that's a traditional interpretation of a series of bits.  But there's
another interpretation we can use: a series of bits may record a bunch of
yes/no answers.  In that sense,

    100010100100

might mean:

    [Yes, No, No, No, Yes, No, Yes, No, No, Yes, No, No]



A bitwise OR allows us to turn any one of those bits from No to Yes.  For
example, perhaps we may like to turn on the very last bit there.  We can
do this by saying:

###
>>> 2212 | 1
2213
###


We should be careful not to interpret the result as an addition: it's not.
We're actually turning on the very last bit, which we can see if we try
doing another OR:

###
>>> 2213 | 1
2213
###

That 'bit' is on already, so doing an OR again doesn't affect the answer.
There are other bitwise operators out there that act like toggle switches;


A bitwise representation of these yes/no choices is nice because it's VERY
compact.  A single integer can normally hold about 32 individual bits.
(32 bit computing!)  And to be able to represent 32 separate 'yes/no'
flags in a single integer is a very neat thing.


We may have run into this sort of thing before: the re.compile() function
can take in an optional set of flags.  For example, we might say something
like:

    re.compile("hello world", re.VERBOSE | re.IGNORECASE)

Without knowing about bits, that statement should actually look weird: how
are we giving two particular bits of information in a single argument?


We can look at what that OR is producing:

###
>>> re.VERBOSE
64
>>> re.IGNORECASE
2
>>> re.VERBOSE | re.IGNORECASE
66
###


It's producing a single integer, but that integer is made up of bits! So
we're really saying that two particular bits should be set to "Yes".

###
>>> int('1000010', 2)
66
###



Does this make sense so far?  A lot of this bit-fiddling just has to deal
with using a very efficient representation for a collection of choices.


Hope this helps!



More information about the Tutor mailing list