从字符串中删除无效的 UTF-8 字符
参考文档: https://www.17golang.com/article/23654.html
我在字符串列表的 json.Marshal 上得到了这个:
json: invalid UTF-8 in string: "...ole\xc5\"
原因很明显,但是如何在 Go 中删除/替换此类字符串?我一直在阅读文档unicode
和unicode/utf8
软件包,似乎没有明显/快速的方法来做到这一点。
例如,在 Python 中,您有一些方法可以删除无效字符,替换为指定字符或严格设置,这会在无效字符上引发异常。我怎样才能在 Go 中做同样的事情?
更新:我的意思是得到异常的原因(恐慌?) - json.Marshal 期望是有效的 UTF-8 字符串中的非法字符。
(非法字节序列如何进入该字符串并不重要,通常的方式 - 错误、文件损坏、其他不符合 unicode 的程序等)
正确答案
例如
package main
import (
"fmt"
"unicode/utf8"
)
func main() {
s := "a\xc5z"
fmt.Printf("%q\n", s)
if !utf8.ValidString(s) {
v := make([]rune, 0, len(s))
for i, r := range s {
if r == utf8.RuneError {
_, size := utf8.DecodeRuneInString(s[i:])
if size == 1 {
continue
}
}
v = append(v, r)
}
s = string(v)
}
fmt.Printf("%q\n", s)
}
输出:
"a\xc5z"
"az"
[常见问题解答 - UTF-8、UTF-16、UTF-32 和 BOM]
问:是否有任何不是由 UTF 生成的字节序列?我应该如何解释它们?
答:没有一个 UTF 可以生成每个任意字节序列。例如,在 UTF-8 中,110xxxxxx2 形式的每个字节后面必须跟 10xxxxxx2 形式的字节。 之类的序列是非法的,绝对不能生成。当在转换或解释过程中遇到这种非法字节序列时,符合 UTF-8 的进程必须将第一个字节 110xxxxx2 视为非法终止错误:例如,要么发出错误信号,要么过滤掉字节,要么用标记表示字节例如 FFFD(替换字符)。在后两种情况下,它将在第二个字节 0xxxxxxx2 处继续处理。
符合要求的进程不得将非法或格式错误的字节序列解释为字符,但是,它可能会采取错误恢复措施。没有一致的过程可以使用不规则的字节序列来编码带外信息。