如何避免使用包含os.system调用的.pyw文件的控制台窗口?

时间:2009-11-19 17:28:40

标签: python windows console windows-console pythonw

如果我将我的代码文件保存为.pyw,则不会出现控制台窗口 - 这就是我想要的 - 但如果代码包含对os.system的调用,我仍然会得到一个讨厌的控制台窗口。我认为这是由对os.system的调用造成的。有没有办法从我的.pyw脚本中执行其他文件而根本不提高控制台窗口?

6 个答案:

答案 0 :(得分:15)

您应该使用subprocess.Popen类传递为startupinfo参数的subprocess.STARTUPINFO类的值实例,其中dwFlags属性包含subprocess.STARTF_USESHOWWINDOW标记和wShowWindow属性持有subprocess.SW_HIDE旗帜。这可以从subprocess.py源代码的阅读行866-868推断出来。当您在pythonw.exe下运行而不打开控制台时,可能还需要将subprocess.CREATE_NEW_CONSOLE标记作为creationflags参数的值传递。

当您使用shell=True时,恰好正确地设置了上述所有内容,但这并不意味着它是一个正确的解决方案。我认为这不是因为它增加了运行命令解释器和解析参数的开销。此外,你应该记住(...)在根据文档从外部输入构造命令字符串的情况下,强烈禁止使用shell = True 子进程模块。

答案 1 :(得分:13)

Piotr描述的解决方案实际上并不像听起来那么复杂。以下是将startupinfo传递给check_call调用以禁止控制台窗口的示例:

startupinfo = subprocess.STARTUPINFO()
startupinfo.dwFlags |= subprocess.STARTF_USESHOWWINDOW

subprocess.check_call(cmd, startupinfo=startupinfo)

由于便捷函数callcheck_callcheck_output**kwargs转发给Popen构造函数,因此不需要使用{{1直接。

答案 2 :(得分:7)

人们有点懒惰......我会选择 @Piotr Dobrogost @Frank S. Thomas 作为答案。

我带来了在Linux和Windows上运行的代码:

import platform
import subprocess
startupinfo = None
if platform.system() == 'Windows':
    import _subprocess  # @bug with python 2.7 ?
    startupinfo = subprocess.STARTUPINFO()
    startupinfo.dwFlags |= _subprocess.STARTF_USESHOWWINDOW
    startupinfo.wShowWindow = _subprocess.SW_HIDE

...后来

args = [exe, ...]
out = subprocess.check_output(args, startupinfo=startupinfo)

Thx guys;)

另外:请注意,使用'call'的以下代码也可以在Python 2.7(在Windows上)上使用上面的'startupinfo'代码:

def run_command(cmd, sin, sout):
    print "Running cmd : %s"%(" ".join(cmd) )
    return subprocess.call( cmd, stdin=sin, stdout=sout, startupinfo=startupinfo)

答案 3 :(得分:5)

如果您想避免启动控制台窗口,可以尝试将subprocess模块(subprocess.Popensubprocess.call或其他)与参数shell=True一起使用。

答案 4 :(得分:1)

似乎'os.popen'不会产生控制台窗口。脚本在'pythonw'下运行。不确定所有情况,但在我的情况下它运作良好。

os.popen(command)

答案 5 :(得分:0)

类似于 @firsthand 所说的,我已经在wxPython用户论坛上读到了“替换”当前正在运行的应用程序,即“command.com”或“CMD.exe” “,当您使用以下内容时使用pyw.exe或pythonw.exe:

os.execl(sys.executable, *([sys.executable]+sys.argv))

请参阅another post

虽然在这种情况下我不知道如何管道io。

我相信这种方法的一个好处是,如果你的操作系统任务栏多次运行你的脚本而没有填满CMD图标。另一种方法是,如果你在任务栏中最小化了几个CMD并开始关闭它们,就不可能知道哪个CMD与哪个pythonw脚本有关。