【问题标题】:Python 2.7 Decoding both UTF-8 and unicode-escape in python causes UnicodeEncodeErrorPython 2.7 在 python 中同时解码 UTF-8 和 unicode-escape 会导致 UnicodeEncodeError
【发布时间】:2018-09-06 15:34:27
【问题描述】:

我有一个 tsv 文件,在某些行中,特定列包含混合格式,例如:Hapoel_Be\u0027er_Sheva_A\u002eF\u002eC\u002e,应该是Hapoel_Be'er_Sheva_A.F.C.

这是我用来读取文件和拆分列的代码:

with open(path, 'rb') as f:
  for line in f:
      cols = line.decode('utf-8').split('\t')
      text = cols[3].decode('unicode-escape') #Here is the column that has the above mentioned mixed format

错误信息:

UnicodeEncodeError: 'ascii' codec can't encode character u'\u0160' in position 6: ordinal not in range(128)

我想知道在读取文件时如何从第一种混合格式转换为另一种?我正在使用 python 2.7。

非常感谢,

【问题讨论】:

  • 这是 python 2 还是 3?
  • @FHTMitchell 抱歉忘记指定。这是python 2.7。

标签: python text unicode encoding compiler-errors


【解决方案1】:

您可以使用ast.literal_eval 将原始字节转换为 unicode

import ast

raw_bytes = br'Hapoel_Be\u0027er_Sheva_A\u002eF\u002eC\u002e'
print(raw_bytes)  # b'Hapoel_Be\u0027er_Sheva_A\u002eF\u002eC\u002e'

unicode_string = ast.literal_eval('"{}"'.format(raw_bytes.decode('utf8')))

unicode_string的输出:

Hapoel_Be'er_Sheva_A.F.C.

更新 - 在 python 2.7 中测试并且很有魅力

【讨论】:

  • 感谢您的努力,但它会触发错误,我认为这是因为我已经在解码整行(问题已相应编辑)。
【解决方案2】:

您可以使用decode('unicode-escape') 将这些十六进制序列转换为字符。

>>> 'Hapoel_Be\\u0027er_Sheva_A\\u002eF\\u002eC\\u002e'.decode('unicode-escape')
u"Hapoel_Be'er_Sheva_A.F.C."

编辑:根据您对问题的更新,您实际上有一个 组合 十六进制序列和 ASCII 范围之外的 Unicode 字符。该错误来自 Python 2.7 尝试在 Unicode 字符串上使用 .decode() 时尝试的自动转换 - decode 仅适用于字节字符串,因此它尝试使用 ASCII 编解码器从 Unicode 转换。 Python 3 不允许这个错误。

要解决此问题,您需要进行双重转换,一次将那些非 ASCII 字符转换为十六进制序列,另一次将它们转换回来。 'unicode-escape' 编解码器会将反斜杠加倍,因此也必须更正这些反斜杠。

>>> print u'Hapoel_Be\\u0027er_Sheva_A\\u002eF\\u002eC\\u002e\u0160'.encode('unicode-escape').replace(b'\\\\u', b'\\u').decode('unicode-escape')
Hapoel_Be'er_Sheva_A.F.C.Š

【讨论】:

  • 该死的比我的好多了
  • @FHTMitchell 我总是认为任何一种eval 都是最后的手段。 Python 的指导原则之一是做某事应该总是有一种明显的方法,但它确实违反了这一原则。
  • @MarkRansom 它导致了一个错误。我将发布更多详细信息和错误消息。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-10-30
  • 2013-05-11
  • 2018-10-02
  • 2012-08-30
  • 2018-01-14
  • 1970-01-01
相关资源
最近更新 更多