我的代码如下:
file = 'C:\\Exe\\First Version\\filename.exe'
os.system(file)
当我运行这个程序时,会引发windowserror,找不到指定的文件。 我发现问题与“第一版”之间的空白有关。 那么,我能找到解决问题的方法吗?
PS: 如果变量'file'将作为arg传递到另一个func中怎么办?
答案 0 :(得分:14)
在路径上放置引号将起作用:
file = 'C:\\Exe\\First Version\\filename.exe'
os.system('"' + file + '"')
但更好的解决方案是使用subprocess
模块:
import subprocess
file = 'C:\\Exe\\First Version\\filename.exe'
subprocess.call([file])
答案 1 :(得分:2)
请尝试用双引号括起来。
file = '"C:\\Exe\\First Version\\filename.exe"'
os.system(file)
答案 2 :(得分:0)
您可以使用名称中包含空格的文件的short name。
file = 'C:\\Exe\\FirstV~1\\filename.exe'
os.system(file)
答案 3 :(得分:0)
我用过这个:
import subprocess, shlex
mycmd='"C:\\Program Files\\7-Zip\\7z" x "D:\\my archive.7z" -o"D:\\extract folder" -aou'
subprocess.run(shlex.split(mycmd))
答案 4 :(得分:0)
的确,os.system
将通过在路径中用引号引起来的二进制文件来启动该路径。 (如果您习惯使用终端,那将是一个非常明显的解决方案。)但是,就其本身而言,这不能解决此功能带来的更痛苦的问题。一旦完成,就可以运行麻烦为您的命令添加参数! (啊!)
所有当前的建议是现在使用subprocess
模块,而不要使用这个陈旧的功能。也可以使用shlx
将平面字符串转换为这些子流程函数的列表。我也遇到了那些方法的问题或痛苦,我不会在上面徘徊...。此外,有时os.system
有时更容易用,只要您想要的只是外壳上的薄包装,它隐式地显示了在控制台上输出流,同步工作等。我当然希望有一个内置函数在外壳上执行这样的命令,例如绝对解析,包装,抽象0 ... >
由于没有“过滤器”,所以这是我的os.system
解决方案补丁。这是从我的开源库中提取的。已在Windows,Mac和Ubuntu Linux上进行了测试。我知道这并不是100%的万无一失,而且棕褐色让人希望它参与其中,但还算不错。
调用此_system()
包装程序(传递要执行的字符串)时,只需将长路径用引号引起来,并同时包含需要使用带引号和不带引号的所有参数。在命令中的第一个“令牌”上,这将删除Mac或Linux上引号并在路径中转义空格。在Windows上,它通过实际解析给定环境上的名称来使用“短名称”。这段代码有些棘手。基本上,它使用批处理机制来进行名称解析,并通过stderr将结果发送回去,目的是解析标准输出上Popen()
结果所得到的结果。您还可以在此处使用工作目录选项,并将其首先设置为替代解决方案。
我想我包括了所有导入内容并定义了您需要的内容。如果我错过了任何一项(复制和粘贴源代码的小节),请告诉我。
from os import system, getcwd, chdir
from subprocess import Popen, PIPE
import platform
__plat = platform.system()
IS_WINDOWS = __plat == "Windows"
IS_LINUX = __plat == "Linux"
IS_MACOS = __plat == "Darwin"
__SCRUB_CMD_TMPL = "{0}{1}"
__DBL_QUOTE = '"'
__SPACE = ' '
__ESC_SPACE = '\\ '
if IS_WINDOWS :
__BATCH_RUN_AND_RETURN_CMD = ["cmd","/K"] # simply assuming cmd is on the system path...
__BATCH_ONE_LINER_TMPLT = "{0} 1>&2\n" # the newline triggers execution when piped in via stdin
__BATCH_ESCAPE_PATH_TMPLT = 'for %A in ("{0}") do @echo %~sA'
from subprocess import STARTUPINFO, STARTF_USESHOWWINDOW
__BATCH_ONE_LINER_STARTUPINFO = STARTUPINFO()
__BATCH_ONE_LINER_STARTUPINFO.dwFlags |= STARTF_USESHOWWINDOW
def _system( cmd, wrkDir=None ):
if wrkDir is not None:
initWrkDir = getcwd()
print( 'cd "%s"' % (wrkDir,) )
chdir( wrkDir )
cmd = __scrubSystemCmd( cmd )
print( cmd )
system( cmd )
print('')
if wrkDir is not None: chdir( initWrkDir )
def __scrubSystemCmd( cmd ):
"""
os.system is more convenient than the newer subprocess functions
when the intention is to act as very thin wrapper over the shell.
There is just one MAJOR problem with it:
If the first character in the command is a quote (to escape a long path
to the binary you are executing), then the limited (undesirable) parsing
built into the function can all fall apart. So, this scrub function
solves that...
"""
if not cmd.startswith( __DBL_QUOTE ): return cmd
cmdParts = cmd[1:].split( __DBL_QUOTE )
safeBinPath = _escapePath( cmdParts[0] )
args = __DBL_QUOTE.join( cmdParts[1:] ) # (the leading space will remain)
return __SCRUB_CMD_TMPL.format( safeBinPath, args )
def _escapePath( path ):
if not IS_WINDOWS: return path.replace(__SPACE, __ESC_SPACE)
return( path if __SPACE not in path else
__batchOneLinerOutput( __BATCH_ESCAPE_PATH_TMPLT.format(path) ) )
def __batchOneLinerOutput( batch ):
cmd = __BATCH_ONE_LINER_TMPLT.format( batch )
p = Popen( __BATCH_RUN_AND_RETURN_CMD, shell=False,
startupinfo=__BATCH_ONE_LINER_STARTUPINFO,
stdin=PIPE, stdout=PIPE, stderr=PIPE )
# pipe cmd to stdin, return stderr, minus a trailing newline
return p.communicate( cmd )[1].rstrip()