我可以在Python中用Popen处理已打开的gzip文件吗?
我有一个小工具,可以在命令行中使用,它会从标准输入(stdin)读取数据。
在命令行中,我可以这样运行它...
./foo < bar
或者这样...
cat bar | ./foo
如果我有一个压缩过的文件,我可以这样运行它
zcat bar.gz | ./foo
在Python中,我可以这样做...
Popen(["./foo", ], stdin=open('bar'), stdout=PIPE, stderr=PIPE)
但是我不能这样做
import gzip
Popen(["./foo", ], stdin=gzip.open('bar'), stdout=PIPE, stderr=PIPE)
结果我不得不这样运行
p0 = Popen(["zcat", "bar"], stdout=PIPE, stderr=PIPE)
Popen(["./foo", ], stdin=p0.stdout, stdout=PIPE, stderr=PIPE)
我是不是做错了什么?为什么我不能把gzip.open('bar')作为Popen的标准输入参数?
1 个回答
4
因为子进程的'标准输入'和'标准输出'使用的是文件描述符(这其实就是一个数字),它是操作系统的一种资源。这个过程有点复杂,因为如果你传递一个对象,子进程模块会检查这个对象是否有'fileno'这个属性,如果有,它就会使用这个属性。
'gzip'对象并不是操作系统提供的东西。打开的文件、套接字和管道都是操作系统能提供的资源。而gzip对象是一个提供read()和write()方法的对象,但它没有'fileno'这个属性。
不过,你可以看看子进程的communicate()方法,你可能会想用到它。