Python子进程回显一个unicode文字
我知道这样的问题之前已经被问到过。 但我没有找到解决方案。
我想在子进程模块中使用我的python文件中定义的unicode文字。 但是我没有得到我需要的结果。 例如下面的代码
# -*- coding: utf-8 -*-
import sys
import codecs
import subprocess
cmd = ['echo', u'你好']
new_cmd = []
for c in cmd:
if isinstance(c,unicode):
c = c.encode('utf-8')
new_cmd.append(c)
subprocess.call(new_cmd)
打印出来
ä½ å¥½
如果我将代码更改为
# -*- coding: utf-8 -*-
import sys
import codecs
import subprocess
cmd = ['echo', u'你好']
new_cmd = []
for c in cmd:
if isinstance(c,unicode):
c = c.encode(sys.getfilesystemencoding())
new_cmd.append(c)
subprocess.call(new_cmd)
我得到以下
??
在这个阶段,我只能假设我一再犯了一个简单的错误。 但我很难搞清楚它是什么。 我怎样才能得到echo通过python的子进程调用时打印出下列内容
你好
编辑:
Python的版本是2.7。 我在Windows 8上运行,但我希望解决方案能够独立于平台。
结论:注意字符编码(这里有三种不同的字符编码)。 如果你想要可移植的Unicode支持(将参数传递为Unicode,不要对它们进行编码),或者确保可以使用来自环境的当前字符编码表示数据(使用Python 2上的sys.getfilesystemencoding()
在第二个代码示例中做)。
第一个代码示例不正确。 效果是一样的(在IDLE中运行 - py -3 -midlelib
):
>>> print(u'你好'.encode('utf-8').decode('mbcs')) #XXX DON'T DO IT!
ä½ å¥½
其中mbcs
编解码器使用您的Windows ANSI代码页(通常为: cp1252
字符编码 - 它可能与例如俄语Windows上的cp1251
不同)。
Python 2使用CreateProcess
宏启动一个子进程,该子进程等同于CreateProcessA
函数。 CreateProcessA
将输入字节解释为使用Windows ANSI编码进行编码。 它与Python源代码编码无关(在你的情况下是utf-8)。
如果你使用错误的编码,预计你会得到mojibake。
如果可以使用Windows代码页(例如cp1252
启用第二个代码示例(如果允许从Unicode编码为字节),并且echo
使用Unicode API打印到Windows控制台,如WriteConsoleW()
(请参阅Python 3包win-unicode-console
- 只要控制台中的字体支持字符,它就可以print(u'你好')
),或者可以使用OEM代码页来表示字符(由cmd.exe
)例如cp437
(运行chcp
找出你的)。 ??
问号表明你好
不能用你的控制台编码表示。
要支持任意的Unicode参数(包括不能用Windows(“ANSI”)或MS-DOS(OEM)代码页表示的字符),需要CreateProcessW
函数(由Python 3使用)。 使用Python和subprocess.Popen()在Windows上查看Unicode文件名。
你的第一次尝试是最好的。
实际上,你转换的2个Unicode字符u'你好'
(或u'u4f60u597d'
在UTF8一切让) b'xe4xbdxa0xe5xa5xbd'
您可以在空闲时完全支持Unicode和地方控制它b'xe4xbdxa0xe5xa5xbd'.decode('utf-8')
还给你好
。 控制它的另一种方法是将脚本输出重定向到一个文件,并用UTF-8兼容的编辑器打开它:在那里你会看到你想要的。
但问题是,Windows控制台不支持完整的Unicode。 这取决于 :
如果你知道一个代码页包含字符的字形(我没有),你可以尝试用chcp
将它插入到控制台中,并且明确地将你的unicode字符串编码到那个字符串中。 但在我的法国机器上,我不知道该怎么做...除了传递一个文本文件!
正如你所说的ConEmu,我做了一个尝试......并且它与python 3.4一起工作正常!
chcp 65001
py -3
import subprocess
cmd = ['cmd', '/c', 'echo', u'u4f60u597d']
subprocess.call(cmd)
给出:
你好
0
问题只出现在cmd.exe
窗口中!