Python UnicodeEncodeError:&x27;charmap';编解码器可以';t编码字符'\x80和x27;在位置0:字符映射到<;未定义>;

Python UnicodeEncodeError:&x27;charmap';编解码器可以';t编码字符'\x80和x27;在位置0:字符映射到<;未定义>;,python,unicode,encoding,Python,Unicode,Encoding,我有一个字符串,它由我的IDE(非常旧的Boa构造函数)自动转换为字节码。 现在我想将其转换为unicode,以便在特定机器上使用编码打印它(windows上的cp1252或Linux上的utf-8) 我用两种不同的方法。其中一个在工作,另一个不工作。但是为什么呢 以下是工作版本: #!/usr/bin/python # vim: set fileencoding=cp1252 : str = '\x80' str = str.decode('cp1252') # to unicode str

我有一个字符串,它由我的IDE(非常旧的Boa构造函数)自动转换为字节码。 现在我想将其转换为unicode,以便在特定机器上使用编码打印它(windows上的cp1252或Linux上的utf-8)

我用两种不同的方法。其中一个在工作,另一个不工作。但是为什么呢

以下是工作版本:

#!/usr/bin/python
# vim: set fileencoding=cp1252 :

str = '\x80'
str = str.decode('cp1252') # to unicode
str = str.encode('cp1252') # to str
print str
#!/usr/bin/python
# vim: set fileencoding=cp1252 :

str = u'\x80'
#str = str.decode('cp1252') # to unicode
str = str.encode('cp1252') # to str
print str
以下是不工作的版本:

#!/usr/bin/python
# vim: set fileencoding=cp1252 :

str = '\x80'
str = str.decode('cp1252') # to unicode
str = str.encode('cp1252') # to str
print str
#!/usr/bin/python
# vim: set fileencoding=cp1252 :

str = u'\x80'
#str = str.decode('cp1252') # to unicode
str = str.encode('cp1252') # to str
print str
在版本1中,我通过decode函数将str转换为unicode。 在版本2中,我通过字符串前面的u将str转换为unicode。
但是我想,这两个版本会做完全相同的事情?

str.decode
不仅仅是在字符串文本前面加上
u
。它将输入字符串的字节转换为有意义的字符(即Unicode)

然后调用
encode
将这些字符转换为字节,因为您需要“打印”,将它们输出到终端或任何其他操作系统实体(如GUI窗口)

因此,关于您的具体任务,我相信您希望:

s = '\x80'
print s.decode('cp1251').encode(platform_encoding)
其中,
'cp1251'
是IDE的编码,
平台_编码
是当前系统编码的变量


在答复你的评论时:


但是str.decode应该使用源代码编码(从 文件中的第2行)进行解码。因此,这两者之间应该没有区别 美国

这是不正确的假设。从

然后,Python解析器使用编码信息来 使用给定的编码解释文件

所以
set fileencoding=cp1252
只是告诉解释器在解析行
str='\x80'
时如何将字符[您通过编辑器输入的]转换为字节。在
str.decode
调用期间不使用此信息

您也在问,u'\x80'是什么
\x80
被简单地解释为
\u0080
,这显然不是您想要的。看看这个问题-。

'\x80'。解码('cp1252')
不会给出
u'\u0080'
(这与
u'\x80'
是一样的)

字节0x80解码为Unicode字符
U+20AC欧元符号

有一种编码,其中所有字节0x00到0xFF解码为具有相同数字U+0000到U+00FF的Unicode字符:它是。通过这种编码,您的示例可以正常工作


Windows
cp1252
与该编码类似,但不同:虽然0xA0到0xFF与
iso-8859-1
中的相同,因此您可以获得这些字符的直接映射行为,但字节0x80到0x9F是来自其他Unicode块的额外符号的组合,而不是不可见的(基本上是无用的)控制代码U+0080至U+009F。

是的,平台编码正确。我想,这样解释比较容易,但是str.decode应该使用源代码编码(来自文件第2行)来解码。所以对美国来说应该没有什么不同。嗨,罗马人,现在我明白了!谢谢我读了之后感到困惑,因为上面写着:u“\xac”。我想,这也适用于u'\x80:)