我在Windows上使用Python 3.6。当我使用标准Windows shell( cmd.exe )运行脚本时, stdin / stdout 的默认文本编码是{3}中的'utf-8'
。 X:
python -c "import sys; print(sys.stdout.encoding)"
utf-8
然而,IDLE shell上的相同命令导致了不同的结果,这显然很烦人,特别是对于使用IDLE作为第一步IDE的初学者
>>> import sys; print(sys.stdout.encoding)
cp1252
IDLE定义了PseudoOutputFile
和PseudoInputFile
类来包装 stdout / stdin 。这些类包含隐藏的_encoding
属性,可用于根据需要切换编码
>>> sys.stdout._encoding = 'utf-8'
>>> print(sys.stdout.encoding)
utf-8
但是每次启动脚本时都会取消此设置,因为IDLE会在运行模块时重新启动其shell。是否有任何长期解决方案可以更改IDLE的 stdin / stdout 的默认编码?
答案 0 :(得分:1)
对于2.7,3.5,您显示的命令行使用cp437 - IBM PC或DOS编码响应。输出到Windows控制台仅限于基本多语言平面(BMP)Unicode字符的子集。
对于3.6,Python对Windows控制台的处理大大改进,使用utf-8并可能打印任何unicode字符,具体取决于字体的可用性。
对于所有当前版本,IDLE还为我报告cp1252(拉丁文1)。由于试图获得系统编码,我不知道为什么会有这种差异。但它几乎没有任何区别,因为它是假的或虚假的价值。对我来说,它具有欺骗性,因为非latin1字符不能用latin1编码,而所有BMP字符都可以用IDLE打印。所以我考虑过替换。
当(unicode)字符串写入sys.stdout(通常带有print)时,字符串对象在用户进程中被腌制为字节,通过套接字(实现详细信息可能会发生变化)发送到IDLE进程,并且未打开回到一个字符串对象。效果就好像字符串是用非损耗的utf编码之一编码和解码的。 UTF-32可能是最接近酸洗的。
IDLE进程调用tkinter text.insert(index,string),它要求tk在小部件中插入字符串。但这只适用于BMP角色。净效应好像输出编码是ucs-2,但我相信tk在内部使用截断的utf-8。
同样,您在shell或编辑器中输入的任何BMP字符都可以在显示后发送到用户进程stdin。
无论如何,更改pseudofile.encoding没有效果,这就是为什么它被issue 9290
的补丁的这一部分设为只读的原因- self.encoding = encoding
+ self._encoding = encoding
+
+ @property
+ def encoding(self):
+ return self._encoding
初始下划线表示_encoding是一个私有(非隐藏)实现细节,应由用户忽略。