Python3 вывод нескольких процессов в один процесс [дубликат]

Клиент ApacheHttp удален в v23 sdk. Вы можете использовать HttpURLConnection или сторонний Http-клиент, например OkHttp.

ref: https://developer.android.com/preview/behavior-changes.html#behavior-apache-http-client

22
задан 12 September 2011 в 15:43
поделиться

4 ответа

Я думаю, вы хотите создать экземпляр двух отдельных объектов Popen, один для «ls», а другой для «sed». Вы хотите передать первый атрибут stdout объекта Popen в качестве аргумента stdin второму объекту Popen.

Пример:

p1 = subprocess.Popen('ls ...', stdout=subprocess.PIPE)
p2 = subprocess.Popen('sed ...', stdin=p1.stdout, stdout=subprocess.PIPE)
print p2.communicate()

Вы можете сохранить цепочку этого если у вас больше команд:

p3 = subprocess.Popen('prog', stdin=p2.stdout, ...)

Дополнительную информацию о работе с подпроцессами см. в документации к подпроцессу .

36
ответ дан Alex Smith 18 August 2018 в 23:08
поделиться
  • 1
    Не могли бы вы показать полный рабочий пример того, как объединить три процесса вместе. Например, я не уверен, сколько раз мне нужно вызвать связь, а когда закрыть stdin и stdout (docs упоминает о закрытии stdout, а ответ ниже показывает закрытие stdin. – Leonid 12 June 2014 в 02:38
  • 2
    @Leonid вам нужно только позвонить один раз в последний процесс, так как вы породили все из них и связали их вместе. Итак, если у вас есть процессы p1, p2, ...., pn, просто вызовите pn.communicate() в конце. – djhaskin987 21 August 2015 в 19:23

Я сделал небольшую функцию, чтобы помочь с трубопроводом, надеюсь, что это поможет. Он будет привязывать Popens по мере необходимости.

from subprocess import Popen, PIPE
import shlex

def run(cmd):
  """Runs the given command locally and returns the output, err and exit_code."""
  if "|" in cmd:    
    cmd_parts = cmd.split('|')
  else:
    cmd_parts = []
    cmd_parts.append(cmd)
  i = 0
  p = {}
  for cmd_part in cmd_parts:
    cmd_part = cmd_part.strip()
    if i == 0:
      p[i]=Popen(shlex.split(cmd_part),stdin=None, stdout=PIPE, stderr=PIPE)
    else:
      p[i]=Popen(shlex.split(cmd_part),stdin=p[i-1].stdout, stdout=PIPE, stderr=PIPE)
    i = i +1
  (output, err) = p[i-1].communicate()
  exit_code = p[0].wait()

  return str(output), str(err), exit_code

output, err, exit_code = run("ls -lha /var/log | grep syslog | grep gz")

if exit_code != 0:
  print "Output:"
  print output
  print "Error:"
  print err
  # Handle error here
else:
  # Be happy :D
  print output
1
ответ дан hernvnc 18 August 2018 в 23:08
поделиться

shlex разделяет пробелы только по правилам оболочки, но не имеет отношения к трубам.

Он должен, однако, работать следующим образом:

import subprocess
import shlex

sp_ls = subprocess.Popen(shlex.split(r'ls -l'), stdin = subprocess.PIPE, stdout = subprocess.PIPE, stderr = subprocess.PIPE)
sp_sed = subprocess.Popen(shlex.split(r'sed "s/a/b/g"'), stdin = sp_ls.stdout, stdout = subprocess.PIPE, stderr = subprocess.PIPE)
sp_ls.stdin.close() # makes it similiar to /dev/null
output = sp_ls.communicate()[0] # which makes you ignore any errors.
print output

согласно к help(subprocess)

Replacing shell pipe line
-------------------------
output=`dmesg | grep hda`
==>
p1 = Popen(["dmesg"], stdout=PIPE)
p2 = Popen(["grep", "hda"], stdin=p1.stdout, stdout=PIPE)
output = p2.communicate()[0]

HTH

2
ответ дан Jacques Gaudin 18 August 2018 в 23:08
поделиться
  • 1
    В примере используется следующая строка: p1.stdout.close() # Allow p1 to receive a SIGPIPE if p2 exits.. Должен ли я использовать его также? – Leonid 12 June 2014 в 02:35
  • 2
    @Leonid Да. Если вы этого не сделаете, p1 попытается написать и не получит уведомление о том, что никто больше не слушает. Так как ваша программа все еще открыта, но не читает, вы получаете тупик. – glglgl 12 June 2014 в 03:19
1
ответ дан Russell 18 August 2018 в 23:08
поделиться
Другие вопросы по тегам:

Похожие вопросы: