Запустите подпроцесс, представляющий собой новую консоль Windows, в которой запускается исполняемый файл.

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

В настоящее время у меня есть сценарий, который запускает n подпроцессов some.exe id, которые я регулярно poll() определяю, завершились ли они, и если да, то с каким уровнем ошибки. Подпроцессы сохраняются в словаре (ключ = подпроцесс, значение = id). n экземпляров some.exe продолжают работать, каждый с собственным идентификатором, до тех пор, пока не будут обработаны все идентификаторы из предопределенного списка.

У some.exe нет графического интерфейса, он записывает прогресс в стандартный вывод, который мне не нужен. Теперь по какой-то причине иногда some.exe не продолжается, как если бы он ждал - таким образом, poll() никогда не выдает уровень ошибки, а done = proc.poll() is not None никогда не бывает истинным. Что рано или поздно приводит к моей диктовке n процессов, все они неактивны, а общий прогресс зависает.

Если запустить вручную в cmd, some.exe с идентификатором, который показывает это поведение в скрипте - работает отлично.

Поэтому моя идея заключалась в том, чтобы запустить новое окно cmd из сценария, который запускает some.exe с идентификатором, но я все равно должен иметь возможность poll() указанного exe.

Вот примерно что у меня есть на данный момент:

while id_list > 0:
    if len(proc_dict) < n:
        id = next_id()
        proc = subprocess.Popen(["some.exe", id], stdout=PIPE)
        proc.poll()
        proc_dict[proc] = id
    else:
        done_procs = []
        for proc in proc_dict.keys():
            done = proc.poll() is not None

            if done:
                print("returncode: "+proc.returncode)
                done_procs.append(proc)

        if done_procs:
            for p in done_procs:
                del proc_dict[p]

        time.sleep(2)

редактировать: если я proc.communicate()[0] в else:, где находится sleep, some.exe может продолжить/завершить, но поскольку communicate ожидает процесса, это слишком сильно замедляет скрипт.


person Daedalus Mythos    schedule 14.10.2014    source источник
comment
Есть ли много вывода на стандартный вывод из some.exe?   -  person GP89    schedule 14.10.2014
comment
Я бы сказал так ... вывод варьируется, но это около 20-100 строк или больше.   -  person Daedalus Mythos    schedule 14.10.2014
comment
У вас все еще возникает проблема, если вы вынимаете stdout=PIPE?   -  person GP89    schedule 14.10.2014
comment
Я только что протестировал его, и, похоже, он работает без stdout=PIPE..! Я достиг какого-то предела там? большое спасибо! Есть ли другой способ подавить стандартный вывод?   -  person Daedalus Mythos    schedule 14.10.2014


Ответы (1)


Я считаю, что проблема в том, что выходных данных some.exe достаточно, чтобы заполнить буфер os pipe, вызывая взаимоблокировку. Предупреждение об этом есть в документах здесь

Если вы хотите отказаться от стандартного вывода, вместо того, чтобы отправлять его в канал, вы можете вместо этого отправить его в devnull, этот пост объясняет как это сделать

person GP89    schedule 14.10.2014