Подтвердить что ты не робот

Input() блокирует другие процессы python в Windows 8 (python 3.3)

Работая над многопоточным кросс-платформенным приложением python3.3, я наткнулся на какое-то странное поведение, которого я не ожидал, и не уверен, что этого не ожидается. Проблема в Windows 8, вызывающая метод input() в одном потоке, блокирует другие потоки, пока не завершится. Я проверил приведенный ниже пример script на трех Linux, двух компьютерах под управлением Windows 7 и Windows 8, и это поведение наблюдается только на компьютере под управлением Windows 8. Является ли это ожидаемым поведением для Windows 8?

test.py:

import subprocess, threading, time

def ui():
    i = input("-->")
    print(i)

def loop():
    i = 0
    f = 'sky.{}'.format(i)
    p = subprocess.Popen(['python', 'copy.py', 'sky1', f])
    t = time.time()
    while time.time() < t+15:
        if p.poll() != None:
            print(i)
            time.sleep(3)
            i+=1
            f = 'sky.{}'.format(i)
            p = subprocess.Popen(['python', 'copy.py', 'sky1', f])
    p.terminate()
    p.wait()

def start():
    t1 = threading.Thread(target=ui)
    t2 = threading.Thread(target=loop)
    t1.start()
    t2.start()
    return t2

t2 = start()
t2.join()
print('done')

copy.py:

import shutil
import sys

src = sys.argv[1]
dst = sys.argv[2]

print('Copying \'{0}\' to \'{1}\''.format(src, dst))
shutil.copy(src, dst)

Обновление: Пробовав одно из предложений, я понял, что я бросился к выводу, лишившись чего-то очевидного. Я приношу свои извинения за то, что вы пришли к ложному началу.

Так как Schollii предложил просто использовать потоки (без подпроцессов или файлов python), все процессы, делающие продвижение вперед, тем самым на самом деле используют input() в одном процессе python, будут блокировать/не запускать другие процессы python (я не точно знаю, что происходит). Кроме того, это, по-видимому, только процессы python, которые затронуты. Если я использую тот же код, показанный выше (с некоторыми изменениями) для выполнения исполняемых файлов, отличных от python, с подпроцессом .Popen они будут работать как ожидалось.

Подводя итог:

  • Использование подпроцесса для выполнения исполняемого файла, отличного от python: работает как ожидалось с помощью и без вызовов input().
  • Использование подпроцесса для выполнения исполняемого файла python: созданные процессы не запускаются, если в исходном процессе выполняется вызов input().
  • Используйте подпроцесс для создания процессов python с вызовом input() в новом процессе, а не в исходном процессе: вызов input() блокирует все процессы python, порожденные "основным" процессом.

Боковое примечание: у меня нет платформы Windows 8, поэтому отладка/тесты могут быть немного медленными.

4b9b3361

Ответ 1

Поскольку в Python 3.0-3.2 существует несколько проблем с input, на этот метод повлияли несколько изменений.

Возможно, у нас снова есть новая ошибка.

Можете ли вы попробовать следующий вариант: raw_input() "back port" (который был доступен в Python 2.x):

...
i = eval(input("-->"))
...

Ответ 2

Это очень хорошая проблема для работы,

так как вы зависите от метода input(), который обычно требуется для ввода в консоль,

поскольку у вас есть потоки, все потоки пытаются связаться с консолью,

Итак, я советую вам использовать концепцию Producer-Consumer или определить все ваши входы в текстовый файл и передать текстовый файл в программу.