【问题标题】:Why compare using bitwise AND in golang?为什么在 golang 中使用按位与比较?
【发布时间】:2019-03-01 05:02:40
【问题描述】:

我正在阅读这样一段代码(取自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:] 
}

我的新手问题是为什么有人会使用像op&amp;Remove == Remove 这样的按位与运算来实际进行比较。 为什么不直接比较 op 和 (Create|Remove|...) 的值呢?

【问题讨论】:

  • 因为您可以指定多个要设置的标志。 op 是一个位模式,如果有人通过 0001010,可以说位 4 表示“重命名”,位 2 表示“写入”,这不等于重命名为 0001000,也不等于写入为 00000010。测试是否设置了重命名位您必须将其与重命名并测试结果是否为非零。与重命名、写入等比较在这里并不重要,可以用 != 0 代替。
  • 您了解iota 的工作原理吗?你知道CreateWriteRemote等的值是什么吗?一旦你明白了,为什么你想使用&amp; 而不是检查相等性可能会变得更清楚......
  • 感谢@Volker!将op&amp;operationnot 零进行比较更直接。我虽然这段代码op&amp;operation==operation 是某种惯用语。

标签: go bitwise-operators bitwise-and


【解决方案1】:

这是bit masking 的示例。他们正在做的是定义一系列掩码(创建、删除、写入),它们是整数 1、2、4、8、16、32 等。您传入一个可以有多个操作的操作值,它会根据翻转的位来确定要执行的操作。如果您以按位模式考虑这些数字,这将更有意义。 4 == 00000100,移除的值。如果您传入一个操作码 6,当您比较 00000110 && 00000100 == 00000100 时,您会得到正确的结果,因为特定于 Remove 的位(第三个最低有效位)是 1。

以一种不那么行话和具体的方式,这基本上是一种用一个字节传递多个操作码的方法。他们进行按位与然后比较的原因是因为它允许他们检查该特定位是否被翻转,而忽略其余位。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-02-13
    • 1970-01-01
    • 2015-01-11
    • 2016-02-14
    • 2023-03-26
    相关资源
    最近更新 更多