本文摘于云游道士 链接:https://www.cnblogs.com/yyds/p/7288916.html

个人简化,便于查询.

命令行指令的执行通常有两个比较关注的结果:

  1. 命令执行的状态码--表示命令执行是否成功
  2. 命令执行的输出结果--命令执行成功后的输出

早期的Python版本中,主要是通过os.system()、os.popen().read()等函数来执行命令行指令的,另外还有一个很少使用的commands模块。从Python 2.4开始官方文档中建议使用的是subprocess模块,重要要介绍的是subprocess模块。subprocess是Python 2.4中新增的一个模块,它允许你生成新的进程,连接到它们的 input/output/error 管道,并获取它们的返回(状态)码。这个模块的目的在于替换几个旧的模块和方法.

subprocess常用参数:(初级应用)

方法 描述
subprocess.run() 执行指定的命令,等待命令执行完成后返回一个包含执行结果的CompletedProcess类的实例
subprocess.call() 执行指定的命令,返回命令执行状态,其功能类似于os.system(cmd)。
subprocess.check_call() 执行指定的命令,如果执行成功则返回状态码,否则抛出异常。其功能等价于subprocess.run(..., check=True)。
subprocess.check_output() 执行指定的命令,如果执行状态码为0则返回命令执行结果,否则抛出异常。
subprocess.getoutput(cmd) 接收字符串格式的命令,执行命令并返回执行结果,其功能类似于os.popen(cmd).read()和commands.getoutput(cmd)。
subprocess.getstatusoutput(cmd) 执行cmd命令,返回一个元组(命令执行状态, 命令执行结果输出),其功能类似于commands.getstatusoutput()。

就使用目的,主要选了subprocess.getoutput(cmd) 和 subprocess.getstatusoutput(cmd) 参数为例.

>>> ret = subprocess.getoutput('ls -l')
>>> print(ret)
总用量 160
drwxr-xr-x 2 wader wader 4096 12月 7 2015 公共的
drwxr-xr-x 2 wader wader 4096 12月 7 2015 模板
drwxr-xr-x 2 wader wader 4096 12月 7 2015 视频
...
>>> retcode, output = subprocess.getstatusoutput('ls -l')
>>> print(retcode)
0
>>> print(output)
总用量 160
drwxr-xr-x 2 wader wader 4096 12月 7 2015 公共的
drwxr-xr-x 2 wader wader 4096 12月 7 2015 模板
drwxr-xr-x 2 wader wader 4096 12月 7 2015 视频
...
drwxr-xr-x 7 wader wader 4096 5月 26 2016 桌面
>>> retcode, output = subprocess.getstatusoutput('ls -l /test')
>>> print(retcode)
2
>>> print(output)
ls: 无法访问/test: 没有那个文件或目录

以上的都是 弱鸡!!! 以下的才是正解! 实际运用可全部跳过,看最后总结!!!!!!

subprocess.Popen

  用于在一个新的进程中执行一个子程序。上面介绍的这些函数都是基于subprocess.Popen类实现的,通过使用这些被封装后的高级函数可以很方面的完成一些常见的需求。由于subprocess模块底层的进程创建和管理是由Popen类来处理的,因此,当无法通过上面哪些高级函数来实现一些不太常见的功能时就可以通过subprocess.Popen类提供的灵活的api来完成。

class subprocess.Popen(args, bufsize=-1, executable=None, stdin=None, stdout=None, stderr=None, preexec_fn=None, close_fds=True, shell=False, cwd=None, env=None, universal_newlines=False, startup_info=None, creationflags=0, restore_signals=True, start_new_session=False, pass_fds=())

参数说明:

  • args: 要执行的shell命令,可以是字符串,也可以是命令各个参数组成的序列。当该参数的值是一个字符串时,该命令的解释过程是与平台相关的,因此通常建议将args参数作为一个序列传递。
  • bufsize: 指定缓存策略,0表示不缓冲,1表示行缓冲,其他大于1的数字表示缓冲区大小,负数 表示使用系统默认缓冲策略。
  • stdin, stdout, stderr: 分别表示程序标准输入、输出、错误句柄。
  • preexec_fn: 用于指定一个将在子进程运行之前被调用的可执行对象,只在Unix平台下有效。
  • close_fds: 如果该参数的值为True,则除了0,1和2之外的所有文件描述符都将会在子进程执行之前被关闭。
  • shell: 该参数用于标识是否使用shell作为要执行的程序,如果shell值为True,则建议将args参数作为一个字符串传递而不要作为一个序列传递。
  • cwd: 如果该参数值不是None,则该函数将会在执行这个子进程之前改变当前工作目录。
  • env: 用于指定子进程的环境变量,如果env=None,那么子进程的环境变量将从父进程中继承。如果env!=None,它的值必须是一个映射对象。
  • universal_newlines: 如果该参数值为True,则该文件对象的stdin,stdout和stderr将会作为文本流被打开,否则他们将会被作为二进制流被打开。
  • startupinfo和creationflags: 这两个参数只在Windows下有效,它们将被传递给底层的CreateProcess()函数,用于设置子进程的一些属性,如主窗口的外观,进程优先级等。

subprocess.Popen类的方法

方法 描述
Popen.poll() 用于检查子进程(命令)是否已经执行结束,没结束返回None,结束后返回状态码。
Popen.wait(timeout=None) 等待子进程结束,并返回状态码;如果在timeout指定的秒数之后进程还没有结束,将会抛出一个TimeoutExpired异常。
Popen.communicate(input=None, timeout=None) 该方法可用来与进程进行交互,比如发送数据到stdin,从stdout和stderr读取数据,直到到达文件末尾。
Popen.send_signal(signal) 发送指定的信号给这个子进程。
Popen.terminate() 停止该子进程。
Popen.kill() 杀死该子进程。

关于communicate()方法的说明:

  • 该方法中的可选参数 input 应该是将被发送给子进程的数据,或者如没有数据发送给子进程,该参数应该是None。input参数的数据类型必须是字节串,如果universal_newlines参数值为True,则input参数的数据类型必须是字符串。
  • 该方法返回一个元组(stdout_data, stderr_data),这些数据将会是字节穿或字符串(如果universal_newlines的值为True)。
  • 如果在timeout指定的秒数后该进程还没有结束,将会抛出一个TimeoutExpired异常。捕获这个异常,然后重新尝试通信不会丢失任何输出的数据。但是超时之后子进程并没有被杀死,为了合理的清除相应的内容,一个好的应用应该手动杀死这个子进程来结束通信。
  • 需要注意的是,这里读取的数据是缓冲在内存中的,所以,如果数据大小非常大或者是无限的,就不应该使用这个方法。

subprocess.Popen使用实例

实例1:

import subprocess

info = subprocess.Popen("ipconfig ",stdout=subprocess.PIPE,shell=True)

print(info.stdout.read().decode("gbk"))
print(type(info.stdout.read()))

实例二:

import subprocess

#第一条
obj = subprocess.Popen(["python"], stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
obj.stdin.write("print(1+2)".encode())
#out为执行后的结果,err为错误信息.
out,err = obj.communicate()
print("输入的信息为:",out)
print("-----------------")
print("错误信息:",err) print("*" * 35) #第二条
obj2 = subprocess.Popen(["python"], stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
obj2.stdin.write("print(x+1)".encode())
out2,err2 = obj2.communicate()
print("输入的信息为:",out2)
print("-----------------")
print("错误信息:",err2)

实例三:

实现类似df -Th | grep data命令的功能,实际上就是实现shell中管道的共功能。

>>>
>>> p1 = subprocess.Popen(['df', '-Th'], stdout=subprocess.PIPE)
>>> p2 = subprocess.Popen(['grep', 'data'], stdin=p1.stdout, stdout=subprocess.PIPE)
>>> out,err = p2.communicate()
>>> print(out)
/dev/vdb1 ext4 493G 4.8G 463G 2% /data
/dev/vdd1 ext4 1008G 420G 537G 44% /data1
/dev/vde1 ext4 985G 503G 432G 54% /data2 >>> print(err)
None

总结:

import subprocess
#subprocess 用于系统交互
#subprocess.Popen()
#有三条管道:
#stdout:输出管道,输出的结果会加入到这个管道中, .read()读取
#stdin:标准输入管道
#stderr:错误输出管道,输入的命令错误后,会将结果加入到这个管道中,.read()读取.当命令执行正常时,管道为None. #info.stdout.read()输出的结果为 二级制数据,在显示时,需要转码. re = input("输入命令:")
info = subprocess.Popen(re,shell=True,stdout=subprocess.PIPE,
stdin=subprocess.PIPE,
stderr=subprocess.PIPE)
print(info.stdout.read().decode("gbk"))

python - 系统交互操作(subprocess)的更多相关文章

  1. 【转】Python之系统交互(subprocess)

    [转]Python之系统交互(subprocess) 本节内容 os与commands模块 subprocess模块 subprocess.Popen类 总结 我们几乎可以在任何操作系统上通过命令行指 ...

  2. Python之系统交互(subprocess)

    本节内容 os与commands模块 subprocess模块 subprocess.Popen类 总结 我们几乎可以在任何操作系统上通过命令行指令与操作系统进行交互,比如Linux平台下的shell ...

  3. python 系统相关操作

    1.文件 open()代开文件或者创建文件 fout=open('oops.txt','wt') print('Oops, I created a file.',file=fout) fout.clo ...

  4. Python 3 利用 subprocess 实现管道( pipe )交互操作读/写通信

    这里我们用Windows下的shell来举例: from subprocess import * #因为是举例,就全部导入了 为了方便你理解,我们用一个很简单的一段代码来说明: 可以看见我们利用Pop ...

  5. Python(文件、文件夹压缩处理模块,shelve持久化模块,xml处理模块、ConfigParser文档配置模块、hashlib加密模块,subprocess系统交互模块 log模块)

    OS模块 提供对操作系统进行调用的接口 os.getcwd() 获取当前工作目录,即当前python脚本工作的目录路径 os.chdir("dirname")  改变当前脚本工作目 ...

  6. MongoDB的聚合操作以及与Python的交互

    上一篇主要介绍了MongoDB的基本操作,包括创建.插入.保存.更新和查询等,链接为MongoDB基本操作. 在本文中主要介绍MongoDB的聚合以及与Python的交互. MongoDB聚合 什么是 ...

  7. Python模块之OS,subprocess

    1.os 模块 简述: os 表示操作系统 该模块主要用来处理与系统相关操作 最常用的是文件操作 打开 获取 写入 删除 复制 重命名 常用操作 os.getcwd() : 返回当前文件所在文件夹路径 ...

  8. python学习道路(day7note)(subprocess模块,面向对象)

    1.subprocess模块   因为方法较多我就写在code里面了,后面有注释 #!/usr/bin/env python #_*_coding:utf-8_*_ #linux 上调用python脚 ...

  9. python 解释器交互模块 -- sys

    sys模块是与python解释器交互的一个接口 sys.argv 命令行参数List,第一个元素是程序本身路径 sys.getdefaultencoding(): 获取系统当前编码,一般默认为asci ...

随机推荐

  1. BZOJ2178 圆的面积并(simpson积分)

    板子题.可以转一下坐标防止被卡.精度和常数实在难以平衡. #include<iostream> #include<cstdio> #include<cmath> # ...

  2. Dumb Bones UVA - 10529(概率dp)

    题意: 你试图把一些多米诺骨牌排成直线,然后推倒它们.但是如果你在放骨牌的时候不小心把刚放的骨牌碰倒了,它就会把相临的一串骨牌全都碰倒, 而你的工作也被部分的破坏了. 比如你已经把骨牌摆成了DD__D ...

  3. tensorflow_mmp

    搭建win10+py3.6+cuda9.1+cudnn7+tf1.5(如果想知道为什么这么搭配,自己去装两天就知道了) tensorflow_gpu......whl下载 剩下的官网下载,cuda9. ...

  4. MT【44】抛物线不常见性质3

    注:S为抛物线的焦点

  5. [luogu3834]静态区间第k小【主席树】

    传送门:https://www.luogu.org/problemnew/show/P3834 题目描述 如题,给定N个整数构成的序列,将对于指定的闭区间查询其区间内的第K小值. 分析 很多人都说是用 ...

  6. Division, UVa 72(暴力求解)

    题目链接:https://vjudge.net/problem/UVA-725 Write a program that finds and displays all pairs of 5-digit ...

  7. NOIP2016 巨凉无比的感言

    打一场比赛检验自己的水平. D1: 我日苟了,考得跟屎一样. 第一题不说了,奇水无比(跟17年相比的话). 第二题,大名鼎鼎啊... 虽然以前看过题解但是实际做起来只会25分暴力...至少比半年前好多 ...

  8. 洛谷 P3951 小凯的疑惑(数学)

    传送门:Problem P3951 https://www.cnblogs.com/violet-acmer/p/9827010.html 参考资料: [1]:http://m.blog.sina.c ...

  9. TCP UDP 数据包过大导致分片情况

    MTU大家都知道,是链路层中的网络对数据帧的一个限制,依然以以太网为例,MTU为1500个字节.一个IP数据报在以太网中 传输,如果它的长度大于该MTU值,就要进行分片传输,使得每片数据报的长度小于M ...

  10. 使用Nginx反向代理和proxy_cache缓存搭建CDN服务器加快Web访问速度

    碰到问题:移动用户访问web服务器www.osyunwei.com很慢解决办法:1.在移动机房放置一台nginx反向代理服务器2.通过域名DNS智能解析,所有移动用户访问www.osyunwei.co ...