我有一个像这样的unicode:
\xE5\xB1\xB1\xE4\xB8\x9C \xE6\x97\xA5\xE7\x85\xA7
我知道这是一个由utf-8
编码的bytes
字符串表示。
请注意,字符串\xE5\xB1\xB1\xE4\xB8\x9C \xE6\x97\xA5\xE7\x85\xA7
本身是<type 'unicode'>
。
如何将其解码为真正的字符串山东 日照
?
如果您打印了unicode
字符串的repr()
输出,那么您似乎遇到了Mojibake,即使用了错误编码解码的字节数据。
首先将其重新编码为字节,然后使用正确的编解码器进行解码。这可能只需要将其编码为Latin-1即可:
unicode_string.encode('latin1').decode('utf8')
这取决于错误解码应用的方式。如果使用了Windows代码页(例如CP1252),即使强制解码超出CP1252范围的UTF-8字节,也可能得到实际上无法重新编码回CP1252的Unicode数据。ftfy
库,它知道如何处理各种编解码器的强制解码乱码文本问题。>>> unicode_string = u'\xE5\xB1\xB1\xE4\xB8\x9C \xE6\x97\xA5\xE7\x85\xA7'
>>> print unicode_string.encode('latin1').decode('utf8')
山东 日照
>>> import ftfy
>>> print ftfy.fix_text(unicode_string)
山东 日照
如果您有字面字符\
,x
,后跟两个数字,则会有另一层编码,其中每个字节都被4个字符替换。您需要首先通过请求Python使用string_escape
编解码来将其解码为实际的字节:
>>> unicode_string = ur'\xE5\xB1\xB1\xE4\xB8\x9C \xE6\x97\xA5\xE7\x85\xA7'
>>> unicode_string
u'\\xE5\\xB1\\xB1\\xE4\\xB8\\x9C \\xE6\\x97\\xA5\\xE7\\x85\\xA7'
>>> print unicode_string.decode('string_escape').decode('utf8')
山东 日照
'string_escape'
是 Python 2 中唯一的编解码器,它生成一个字节串,因此将其解码为 UTF-8 是安全的。
{u'qualifier': u'name', u'timestamp': u'1462275769186', u'value': u'\\xE5\\x8E\\x9F\\xE6\\x9D\\xA5\\xE6\\x98\\xAFolivia\\xE5\\x95\\x8A', u'columnFamily': u'interActive', u'type': u'Put', u'row': u'1771897264'}
,而且print m.get('value').encode('latin1').decode('utf8')
仍然会打印出\xE5\x8E\x9F...
。 - armnotstrongx
字符和十六进制数字。你在这里有一个不同的问题。是什么产生了这个问题? - Martijn Pietersrepr()
输出(这就是你在评论中显示的dict()
表示形式所使用的每个键和值)。 - Martijn Pietersorg.apache.spark.examples.pythonconverters.HBaseResultToStringConverter
则提供了这个功能。 - armnotstrong