python 运行shell命令的几种方法(os.system、os.popen、subprocess、commands)

1、os.system

该函数返回命令执行结果的返回值,并不是返回命令的执行输出,

system()函数在执行过程中进行了以下三步操作: 1.fork一个子进程; 2.在子进程中调用exec函数去执行命令; 3.在父进程中调用wait(阻塞)去等待子进程结束。

对于fork失败,system()函数返回-1。 ****

用法示例

>>> os.system('ls -a')
.  ..  .bash_logout  .bash_profile  .bashrc  # 执行命令的标准输出
0  # 返回值

注意:system是阻塞的

2、os.popen

os.popen(command[, mode[, bufsize]])

参数

command – 使用的命令。

mode – 模式权限可以是 ‘r’(默认) 或 ‘w’。

bufsize – 指明了文件需要的缓冲大小:0意味着无缓冲;1意味着行缓冲;其它正值表示使用参数大小的缓冲(大概值,以字节为单位)。负的bufsize意味着使用系统的默认值,一般来说,对于tty设备,它是行缓冲;对于其它文件,它是全缓冲。如果没有改参数,使用系统的默认值。

说明

popen() 创建一个管道,通过fork一个子进程,然后该子进程执行命令。返回值在标准IO流中,该管道用于父子进程间通信。父进程要么从管道读信息,要么向管道写信息,至于是读还是写取决于父进程调用popen时传递的参数(w或r)

用法示例

>>> ret = os.popen('ls -a').read()
>>> ret
'.\n..\n.bash_logout\n.bash_profile\n.bashrc\n'

将命令执行结果返回给ret,由于是管道,需要通过read()来获取内容

3、subprocess 模块

subprocess 模块有比较多的功能,这里只讲用来运行shell命令的几个方法

subprocess.call()
父进程等待子进程完成
返回退出信息(returncode,相当于Linux exit code)

与os.system功能相似

subprocess.check_call()

父进程等待子进程完成
返回0
检查退出信息,如果returncode不为0,则举出错误subprocess.CalledProcessError,该对象包含有returncode属性,可用try…except…来检查

subprocess.Popen()

class Popen(args, bufsize=0, executable=None, stdin=None, stdout=None, stderr=None, preexec_fn=None, close_fds=False, shell=False, cwd=None, env=None, universal_newlines=False, startupinfo=None, creationflags=0)

常用参数

args:shell命令,可以是字符串,或者序列类型,如list,tuple。

bufsize:缓冲区大小,可不用关心

stdin,stdout,stderr:分别表示程序的标准输入,标准输出及标准错误

shell:与上面方法中用法相同

cwd:用于设置子进程的当前目录

env:用于指定子进程的环境变量。如果env=None,则默认从父进程继承环境变量

universal_newlines:不同系统的的换行符不同,当该参数设定为true时,则表示使用\n作为换行符

注意:Popen对象创建后,主程序不会自动等待子进程完成。我们必须调用对象的wait()方法,父进程才会等待

不用wait

def no_wait_subprocess():
    child = subprocess.Popen(['ping','-c','4','www.baidu.com'])
    print 'print test'

# 运行结果
print test
[root@]# PING www.a.shifen.com (14.215.177.39) 56(84) bytes of data.
64 bytes from 14.215.177.39 (14.215.177.39): icmp_seq=1 ttl=55 time=7.56 ms
64 bytes from 14.215.177.39 (14.215.177.39): icmp_seq=2 ttl=55 time=6.86 ms
64 bytes from 14.215.177.39 (14.215.177.39): icmp_seq=3 ttl=55 time=8.86 ms
64 bytes from 14.215.177.39 (14.215.177.39): icmp_seq=4 ttl=55 time=6.74 ms

--- www.a.shifen.com ping statistics ---
4 packets transmitted, 4 received, 0% packet loss, time 2999ms
rtt min/avg/max/mdev = 6.748/7.510/8.868/0.844 ms

使用wait

def wait_subprocess():
    child = subprocess.Popen(['ping','-c','4','blog.csdn.net'])
    child.wait()
    print 'print test'

PING blog.csdn.net (39.96.132.69) 56(84) bytes of data.
64 bytes from 39.96.132.69 (39.96.132.69): icmp_seq=1 ttl=89 time=38.8 ms
64 bytes from 39.96.132.69 (39.96.132.69): icmp_seq=2 ttl=89 time=38.4 ms
64 bytes from 39.96.132.69 (39.96.132.69): icmp_seq=3 ttl=89 time=38.0 ms
64 bytes from 39.96.132.69 (39.96.132.69): icmp_seq=4 ttl=89 time=38.4 ms

--- blog.csdn.net ping statistics ---
4 packets transmitted, 4 received, 0% packet loss, time 2998ms
rtt min/avg/max/mdev = 38.085/38.445/38.827/0.327 ms
print test

上面两个例子对比可以看出有wait的先等popen中命令运行完后再执行下一步

上面的subprocess.Popen运行命令是使用list的方法,也可以使用另一种

subprocess.Popen(‘ping -c 4 blog.csdn.net’,shell=True)

4、commands模块

commands.getstatusoutput()

获取返回状态和运行结果

用法示例:

>>> (status, output) = commands.getstatusoutput('ls -a')
>>> print status, output
0 .
..
.bash_logout
.bash_profile
.bashrc

commands.getoutput()

>>> output = commands.getoutput('ls -a')
>>> print output
.
..
.bash_logout
.bash_profile
.bashrc

commands.py源码分析:

__all__ = ["getstatusoutput","getoutput","getstatus"] #这里提供了三种方法

# Get 'ls -l' status for an object into a string
#
def getstatus(file):
    """Return output of "ls -ld <file>" in a string."""
    import warnings
    warnings.warn("commands.getstatus() is deprecated", DeprecationWarning, 2)
    return getoutput('ls -ld' + mkarg(file))


# Get the output from a shell command into a string.
# The exit status is ignored; a trailing newline is stripped.
# Assume the command will work with '{ ... ; } 2>&1' around it..
#
def getoutput(cmd):
    """Return output (stdout or stderr) of executing cmd in a shell."""
    return getstatusoutput(cmd)[1]


# Ditto but preserving the exit status.
# Returns a pair (sts, output)
# 这里是对os.popen的封装处理
def getstatusoutput(cmd):
    """Return (status, output) of executing cmd in a shell."""
    import os
    pipe = os.popen('{ ' + cmd + '; } 2>&1', 'r')
    text = pipe.read()
    sts = pipe.close()
    if sts is None: sts = 0
    if text[-1:] == '\n': text = text[:-1]
    return sts, text

  • 1
    点赞
  • 23
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
`os.system`、`os.popen`和`subprocess.Popen`都是用于在Python程序中调用系统命令的函数,但是它们在用法和功能上有所不同。 1. `os.system` `os.system`函数用于在操作系统中执行命令,并返回执行结果。它的使用方法是: ```python import os os.system('command') ``` 其中,`command`是要执行的命令,可以是任何在操作系统中可执行的命令。`os.system`函数将返回命令的退出状态码,通常情况下,0表示执行成功,其他值表示执行失败。 2. `os.popen` `os.popen`函数用于在操作系统中执行命令,并返回命令的输出。它的使用方法是: ```python import os output = os.popen('command').read() ``` 其中,`command`是要执行的命令,`output`是命令的输出结果,它是一个字符串类型的变量。`os.popen`函数将执行命令,并将命令的输出保存到`output`中。 3. `subprocess.Popen` `subprocess.Popen`函数也用于在操作系统中执行命令,但是它提供了更丰富的控制和选项。它的使用方法是: ```python import subprocess p = subprocess.Popen('command', stdout=subprocess.PIPE, shell=True) output, errors = p.communicate() ``` 其中,`command`是要执行的命令,`stdout=subprocess.PIPE`表示将命令的输出保存到`output`中,`shell=True`表示可以执行shell命令。`subprocess.Popen`函数将执行命令,并返回一个Popen对象,通过Popen对象可以控制命令的执行和获取命令的输出。 以上是三种调用系统命令方法的区别和用法。总体来说,`os.system`函数用于简单的命令调用,`os.popen`函数用于获取命令的输出,`subprocess.Popen`函数用于更复杂的命令调用和控制。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值