two*_*two 13
正如Tim Cooper所说,你可以测试UTF-8的有效性utf8.Valid.
但!您可能认为将非UTF-8字节转换为Go string是不可能的.实际上,"在Go中,字符串实际上是一个只读字节片段" ; 它可以包含无效的UTF-8字节,您可以打印,通过索引访问,甚至往返往[]byte(Write比如说).
Go中有两个地方可以string为你做UTF-8解码.
for i, r := range s,rUnicode代码点是一个类型的值rune[]rune(s),Go会将整个字符串解码为符文在这两种情况下,无效的UTF-8都替换U+FFFD为替换字符,为此类用途保留.有关s和其他类型之间的for语句和转换string的规范部分中有更多内容.这些转换永远不会崩溃,因此您只需要主动检查UTF-8的有效性,如果它与您的应用程序相关,就像您想要在错误编码的输入上抛出错误一样.
由于这种行为已经融入了语言,因此您也可以从库中获得它.U+FFFD是utf8.RuneError由函数返回utf8.
这是一个示例程序,显示Go对[]byte保持无效的UTF-8的作用:
package main
import "fmt"
func main() {
a := []byte{0xff}
s := string(a)
fmt.Println(s)
for _, r := range s {
fmt.Println(r)
}
rs := []rune(s)
fmt.Println(rs)
}
Run Code Online (Sandbox Code Playgroud)
在不同的环境中输出看起来会有所不同,但在Playground看起来很像
?
65533
[65533]
Run Code Online (Sandbox Code Playgroud)