【问题标题】:To make Golang rune to utf-8 result same as js string.fromCharCode使 Golang rune 到 utf-8 结果与 js string.fromCharCode 相同
【发布时间】:2022-10-04 18:12:37
【问题描述】:

var int32s = []int32{
  8, 253, 80, 56, 30, 220, 217, 42, 235, 33, 211, 23, 231, 216, 234, 26,
}

fmt.Println("word: ", string(int32s))

js

let int32s = [8, 253, 80, 56, 30, 220, 217, 42, 235, 33, 211, 23, 231, 216, 234, 26]
str = String.fromCharCode.apply(null, int32s);
console.log("word: " + String.fromCharCode.apply(null, int32s))

上面的2个结果对于一些空字符是不一样的 是否有任何解决方案可以修改 go 代码以生成与 js 相同的结果?

【问题讨论】:

    标签: javascript go fromcharcode rune


    【解决方案1】:

    引用the docs on String.fromCharCode

    静态String.fromCharCode() 方法返回从UTF-16 代码单元的指定序列创建的字符串。

    因此,int32s 数组中的每个数字都被解释为提供 Unicode 代码单元的 16 位整数,因此整个序列被解释为一系列代码单元形成一个 UTF-16 编码的字符串。
    我要强调最后一点,因为从变量的命名来看——int32s,无论谁是 JS 代码的作者,他们似乎对那里发生的事情有错误的认识。

    现在回到 Go 对应物。 Go 没有对 UTF-16 编码的内置支持;它的字符串通常使用UTF-8 编码(尽管它们不是必需的,但我们不要离题),并且 Go 还提供了 rune 数据类型,它是 int32 的别名。 符文是一个 Unicode 代码点,即能够包含完整 Unicode 字符的数字。 (稍后我会回到这个事实及其与 JS 代码的关系。)

    现在,您的string(int32s) 的问题在于它以与[]rune 相同的方式解释您的int32s 切片(请记住runeint32 的别名),因此它包含每个数字切片来表示单个 Unicode 字符并生成它们的字符串。 (此字符串在内部编码为 UTF-8,但这一事实与问题并不真正相关。)

    换句话说,区别在于:

    • JS 代码将数组解释为表示 UTF-16 编码字符串的 16 位值序列,并将其转换为某种内部字符串表示形式。
    • Go 代码将切片解释为 32 位 Unicode 代码点序列,并生成包含这些代码点的字符串。

    Go 标准库生成了一个包来处理 UTF-16 编码:encoding/utf16,我们可以使用它来完成 JS 代码编码的工作——将 UTF-16 编码的字符串解码为一系列 Unicode 代码点,这然后我们可以转换为 Go 字符串:

    package main
    
    import (
        "fmt"
        "unicode/utf16"
    )
    
    func main() {
        var uint16s = []uint16{
            8, 253, 80, 56, 30, 220, 217, 42, 235, 33, 211, 23, 231, 216, 234, 26,
        }
    
        runes := utf16.Decode(uint16s)
    
        fmt.Println("word: ", string(runes))
    }
    

    Playground

    (请注意,我已将切片的类型更改为 []unit16 并相应地重命名它。此外,我已将源切片解码为显式命名的变量;这样做是为了清楚起见——以突出显示正在发生的事情。)

    此代码产生的乱码与 Firefox 控制台中的 JS 代码相同。

    【讨论】:

      猜你喜欢
      • 2017-09-18
      • 1970-01-01
      • 2015-05-02
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多