string - Go:将 rune (字符串)转换为二进制的字符串表示形式

标签 string go binary type-conversion

这只是为了防止其他人正在学习 Golang 并且想知道如何将字符串转换为二进制的字符串表示形式。

长话短说,我一直在查看标准库,但找不到正确的调用。所以我从类似于以下内容开始:

func RuneToBinary(r rune) string {
    var buf bytes.Buffer
    b := []int64{128, 64, 32, 16, 8, 4, 2, 1}
    v := int64(r)
    for i := 0; i < len(b); i++ {
        t := v-b[i]
        if t >= 0 {
           fmt.Fprintf(&buf, "1")
           v = t
        } else {
           fmt.Fprintf(&buf, "0")
        }
    }

    return buf.String()
}

这一切都很好,但在环顾四周后我发现我应该一直使用 fmt而是打包并用 %b% 格式化 rune:

var r rune
fmt.Printf("input: %b ", r)

有更好的方法吗?

谢谢

最佳答案

标准库支持

fmt.Printf("%b", r) - 这个解决方案已经非常紧凑,易于编写和理解。如果您需要作为 string 的结果,您可以使用模拟 Sprintf()功能:

s := fmt.Sprintf("%b", r)

您还可以使用 strconv.FormatInt()该函数采用多个类型 int64(因此您首先必须转换您的 rune)和一个可以传递 2 以获取结果二进制表示:

s := strconv.FormatInt(int64(r), 2)

请注意,在 Go 中,rune 只是 int32 的别名,这两种类型是相同的(只是您可以通过 2 个名称来引用它)。

手动执行(“简单但天真”):

如果您想“手动”执行此操作,则有一个比您原来的解决方案简单得多的解决方案。您可以使用 r & 0x01 == 0 测试最低位,并使用 r >>= 1 移动所有位。只需“循环”所有位并根据位附加 “1”“0”:

请注意,这只是为了演示,它在性能方面远未达到最佳状态(生成“冗余”字符串):

func RuneToBin(r rune) (s string) {
    if r == 0 {
        return "0"
    }
    for digits := []string{"0", "1"}; r > 0; r >>= 1 {
        s = digits[r&1] + s
    }
    return
}

注意:函数不处理负数。如果你还想处理负数,你可以先检查它,然后处理它的正值,返回值以负号 '-' 开始。这也适用于下面的其他手动解决方案。

手动性能解决方案:

为了快速解决方案,我们不应该附加字符串。由于 Go 中的字符串只是使用 UTF-8 编码的字节 slice ,附加一个数字只是附加 rune '0''1' 的字节值,这只是一个字节(不是多个)。所以我们可以分配一个足够大的缓冲区/数组(rune 是 32 位,所以最多 32 个二进制数字),并向后填充它,这样我们甚至不必在最后反转它。并在最后返回转换为 string 的数组的使用部分。请注意,我什至没有调用内置的 append 函数来附加二进制数字,我只是设置了我在其中构建结果的数组的相应元素:

func RuneToBinFast(r rune) string {
    if r == 0 {
        return "0"
    }
    b, i := [32]byte{}, 31
    for ; r > 0; r, i = r>>1, i-1 {
        if r&1 == 0 {
            b[i] = '0'
        } else {
            b[i] = '1'
        }
    }
    return string(b[i+1:])
}

关于string - Go:将 rune (字符串)转换为二进制的字符串表示形式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28659193/

相关文章:

android - 将字符串转换为 JSON 数组时出错

database - 如何使用没有循环指针的反射在 Golang 中调用 Scan variadic 函数?

go - 我应该如何向 gzip writer 添加缓冲?

arrays - 在 Go 中,为什么 a[1 :] not give an index out of bounds error for a capacity = 1 slice?

c++ - 将整数写入二进制文件 C++ 的问题

java - Flex 中的二进制套接字和策略文件

mysql - 查询二进制列以获取多行的所有结果

c# - 使用 Replace() 从开头删除引号会将它们全部删除

Java - 反转字符串空错误

python - 将 numpy 二进制字符串数组转换回字符串