解码 JSON 字符串中的 UTF-8 编码

新手上路,请多包涵

我有包含以下编码字符串的 JSON 文件:

"sender_name": "Horn\u00c3\u00adkov\u00c3\u00a1",

我正在尝试使用 json 模块解析此文件。但是我无法正确解码这个字符串。

使用 .load() 方法解码 JSON 后得到的是 'HornÃ\xadková' 。该字符串应正确解码为 'Horníková'

我阅读了 JSON 规范,我理解在 \u 之后应该有 4 个十六进制数字指定 _Unicode 字符数_。但似乎在此 JSON 文件中, UTF-8 编码字节 存储为 \u 序列。

这是什么类型的编码以及如何在 Python 3 中正确解析它?

根据规范,这种类型的 JSON 文件甚至是有效的 JSON 文件吗?

原文由 Matej Kormuth 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 1.6k
2 个回答

您的文本已经编码,您需要通过在字符串中使用 b 前缀来告诉 Python,但是由于您使用的是 json 并且输入需要是字符串,因此您必须手动解码编码文本。由于您的输入不是字节,您可以使用 'raw_unicode_escape' 编码将字符串转换为字节而不进行编码,并防止 open 方法使用其自己的默认编码。然后您可以简单地使用上述方法来获得所需的结果。

请注意,由于您需要进行编码和解码,因此您必须读取文件内容并对加载的字符串执行编码,因此您应该使用 json.loads() 而不是 json.load()

 In [168]: with open('test.json', encoding='raw_unicode_escape') as f:
     ...:     d = json.loads(f.read().encode('raw_unicode_escape').decode())
     ...:

In [169]: d
Out[169]: {'sender_name': 'Horníková'}

原文由 Mazdak 发布,翻译遵循 CC BY-SA 4.0 许可协议

您正在阅读的 JSON 写入错误,从中解码的 Unicode 字符串必须使用错误的编码重新编码,然后使用正确的编码解码。

这是一个例子:

 #!python3
import json

# The bad JSON you have
bad_json = r'{"sender_name": "Horn\u00c3\u00adkov\u00c3\u00a1"}'
print('bad_json =',bad_json)

# The wanted result from json.loads()
wanted = {'sender_name':'Horníková'}

# What correctly written JSON should look like
good_json = json.dumps(wanted)
print('good_json =',good_json)

# What you get when loading the bad JSON.
got = json.loads(bad_json)
print('wanted =',wanted)
print('got =',got)

# How to correct the mojibake string
corrected_sender = got['sender_name'].encode('latin1').decode('utf8')
print('corrected_sender =',corrected_sender)

输出:

 bad_json = {"sender_name": "Horn\u00c3\u00adkov\u00c3\u00a1"}
good_json = {"sender_name": "Horn\u00edkov\u00e1"}
wanted = {'sender_name': 'Horníková'}
got = {'sender_name': 'HornÃ\xadková'}
corrected_sender = Horníková

原文由 Mark Tolonen 发布,翻译遵循 CC BY-SA 4.0 许可协议

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题