trikelef
trikelef

Reputation: 2204

Why compare using bitwise AND in golang?

I am reading a piece of code like this (taken from fsnotify):

    type Op uint32

    const (
        Create Op = 1 << iota
        Write
        Remove
        Rename
        Chmod
    )

    ...

    func (op Op) String() string {

    var buffer bytes.Buffer

    if op&Create == Create {
        buffer.WriteString("|CREATE")
    }
    if op&Remove == Remove {
        buffer.WriteString("|REMOVE")
    }
    if op&Write == Write {
        buffer.WriteString("|WRITE")
    }
    if op&Rename == Rename {
        buffer.WriteString("|RENAME")
    }
    if op&Chmod == Chmod {
        buffer.WriteString("|CHMOD")
    }
    if buffer.Len() == 0 {
        return ""
    }
    return buffer.String()[1:] 
}

My newbie question is why someone would use a bitwise AND operation like op&Remove == Remove to actually make a comparison. Why not just compare the op and (Create|Remove|...) values?

Upvotes: 0

Views: 1500

Answers (1)

Shane Tyler Malachow
Shane Tyler Malachow

Reputation: 161

This is an example of bit masking. What they're doing is defining a series of masks (Create, Remove, Write) that are integers 1,2,4,8,16,32,etc. You pass in a single op value, which can have multiple operations, and it figures out which operation to perform based on which bit is flipped. This makes more sense if you think about these numbers in a bitwise pattern. 4 == 00000100, the value for Remove. If you pass in an op code of say, 6, when you compare 00000110 && 00000100 == 00000100 you get true, because the bit that is specific to Remove, the third least significant bit, is 1.

In a less jargony and specific way, this is basically a way to pass in multiple opcodes with one byte. The reason they're doing a bitwise AND and then comparing is because it allows them to check if that specific bit is flipped, while ignoring the rest of the bits.

Upvotes: 6

Related Questions