新手python子进程:"写入错误:断管"

mat*_*ick 13 python subprocess popen

感谢以下有用的建议:

所以我似乎已经修好了

  1. 将命令分离为对Popen的单独调用
  2. stderr = subprocess.PIPE作为每个Popen链的参数.

新代码:

import subprocess
import shlex
import logging

def run_shell_commands(cmds):
    """ Run commands and return output from last call to subprocess.Popen.
        For usage see the test below.
    """
    # split the commands
    cmds = cmds.split("|")
    cmds = list(map(shlex.split,cmds))

    logging.info('%s' % (cmds,))

    # run the commands
    stdout_old = None
    stderr_old = None
    p = []
    for cmd in cmds:
        logging.info('%s' % (cmd,))
        p.append(subprocess.Popen(cmd,stdin=stdout_old,stdout=subprocess.PIPE,stderr=subprocess.PIPE))
        stdout_old = p[-1].stdout
        stderr_old = p[-1].stderr
    return p[-1]


pattern = '"^85567      "'
file = "j"

cmd1 = 'grep %s %s | sort -g -k3 | head -10 | cut -d" " -f2,3' % (pattern, file)
p = run_shell_commands(cmd1)
out = p.communicate()
print(out)
Run Code Online (Sandbox Code Playgroud)

原帖:

我花了太长时间试图解决一个简单的子进程问题.Popen.

码:

import subprocess
cmd = 'cat file | sort -g -k3 | head -20 | cut -f2,3' % (pattern,file)
p = subprocess.Popen(cmd,shell=True,stdout=subprocess.PIPE)
for line in p.stdout:
    print(line.decode().strip())
Run Code Online (Sandbox Code Playgroud)

文件输出~1000行的长度:

...
sort: write failed: standard output: Broken pipe
sort: write error
Run Code Online (Sandbox Code Playgroud)

文件输出> 241行的长度:

...
sort: fflush failed: standard output: Broken pipe
sort: write error
Run Code Online (Sandbox Code Playgroud)

文件输出<241行的长度很好.

我一直在阅读文档和谷歌搜索疯狂,但有一些基本的东西模块,我缺少...也许与缓冲区.我尝试过p.stdout.flush()并使用缓冲区大小和p.wait().我试图用'睡眠20;等命令重现这一点; cat moderatefile'但这似乎运行没有错误.

Pau*_*ine 12

子流程文档的配方:

# To replace shell pipeline like output=`dmesg | grep hda`
p1 = Popen(["dmesg"], stdout=PIPE)
p2 = Popen(["grep", "hda"], stdin=p1.stdout, stdout=PIPE)
output = p2.communicate()[0]
Run Code Online (Sandbox Code Playgroud)

  • 我认为大输出要避免沟通? (3认同)

mde*_*ous 5

这是因为你不应该在传递的命令中使用"shell管道" subprocess.Popen,你应该使用subprocess.PIPE如下:

from subprocess import Popen, PIPE

p1 = Popen('cat file', stdout=PIPE)
p2 = Popen('sort -g -k 3', stdin=p1.stdout, stdout=PIPE)
p3 = Popen('head -20', stdin=p2.stdout, stdout=PIPE)
p4 = Popen('cut -f2,3', stdin=p3.stdout)
final_output = p4.stdout.read()
Run Code Online (Sandbox Code Playgroud)

但我不得不说你想要做的事情可以在纯python中完成,而不是调用一堆shell命令.

  • 我正在获得1300多万行返回100k +行匹配,排序,切割和"头".这需要几秒钟的shell.它在python中永远占据了一席之地.我试过read(),我以为我试过拆分命令,但我认为这是同样的问题.测试后会发回更多... (4认同)