Я новичок в Python, и мне хотелось бы найти способ проверить, смогу ли я завершить все процессы одновременно, когда получу желаемый результат, и поместить его в один из процессов. Я пробовал много вещей, таких как sys.exit()
и другие вещи, но это никогда не работало.
Это мой код
import requests
import multiprocessing
import time
start_time = time.time()
def one():
global start_time
for n in range(1000, 4000):
answer = requests.post('https://www.guessthepin.com/prg.php', data = {'guess': n})
if "Holy Moley!" not in str(answer.text):
print("The pin is not", n)
continue
print(f"THE PIN IS: {n}")
end_time = time.time()
print(f"Time taken: {(end_time - start_time) / 60} minutes")
sys.exit()
def two():
global start_time
for n in range(4000, 7000):
answer = requests.post('https://www.guessthepin.com/prg.php', data = {'guess': n})
if "Holy Moley!" not in str(answer.text):
print("The pin is not", n)
continue
print(f"THE PIN IS: {n}")
end_time = time.time()
print(f"Time taken: {(end_time - start_time) / 60} minutes")
sys.exit()
def three():
global start_time
for n in range(7000, 10000):
answer = requests.post('https://www.guessthepin.com/prg.php', data = {'guess': n})
if "Holy Moley!" not in str(answer.text):
print("The pin is not", n)
continue
print(f"THE PIN IS: {n}")
end_time = time.time()
print(f"Time taken: {(end_time - start_time) / 60} minutes")
sys.exit()
def four():
global start_time
for n in range(0, 1000):
zero_thousand = f'{n:04}'
request = requests.post('https://www.guessthepin.com/prg.php', data = {'guess': zero_thousand})
if "Holy Moley!" not in str(request.text):
print("The pin is not", zero_thousand)
continue
print(f"THE PIN IS: {n}")
end_time = time.time()
print(f"Time taken: {(end_time - start_time) / 60} minutes")
sys.exit()
if __name__ == "__main__":
start_time = time.time()
p1 = multiprocessing.Process(target=one)
p2 = multiprocessing.Process(target=two)
p3 = multiprocessing.Process(target=three)
p4 = multiprocessing.Process(target=four)
p1.start()
p2.start()
p3.start()
p4.start()
p1.join()
p2.join()
p3.join()
p4.join()
print("Done!")
end_time = time.time()
print(f"Time taken: {(end_time - start_time)/60} minutes")
Итак, я хотел отправить запросы на веб-сайт, проверить правильность PIN-кода и двигаться дальше. Несмотря на то, что часть запросов работает, когда я использую многопроцессорность и получаю правильный PIN-код, вместо завершения всех процессов она продолжает работать до тех пор, пока не проверит все числа.
как мне выйти из цикла? потому что ничего из того, что я пытаюсь сделать, не работает
Что именно вы хотите сделать? Все ваши процессы завершаются автоматически, когда они завершают выполнение 1000 итераций. Нет необходимости использовать sys.exit()
. После оператора print
функция в процессе завершается, и процесс закрывается.
в моем коде есть несколько функций. Я хочу, чтобы после срабатывания события все мои процессы останавливались. Всякий раз, когда я пытаюсь остановить их всех, у меня ничего не получается. Например, когда я нахожу булавку, останавливается только один процесс, а остальные продолжаются до завершения итерации.
Кроме того, если посмотреть на ваши функции one
, two
и т. д., окажется, что вместо многопоточности можно использовать многопоточность.
Я думаю, что самое простое решение — использовать многопроцессорный пул размером 4, созданный с помощью multiprocessing.pool.Pool(4)
. Затем вы можете отправить в пул 4 «задачи», которые необходимо выполнить, указав обратный вызов, который будет вызываться после завершения задачи. Первая задача, которую необходимо выполнить, вызовет terminate
в пуле, что завершит выполнение других отправленных задач.
Я бы также предложил каждой задаче выполнять start_time = time.time()
, а не наследовать глобальный start_time
(оператор global start_time
в любом случае не требуется), поскольку каждая задача будет начинаться в разное время. И не стоит звонить sys.exit()
. Вам также следует прочитать PEP 8 – Руководство по стилю кода Python.
Обновлять
Поскольку ваши функции one
.. four
идентичны, за исключением диапазонов поиска, и four
передает аргумент POST другого типа, эти четыре функции можно заменить одной функцией. Рабочая функция также возвращает True
, если находит искомую строку:
import time
import requests
USE_THEADING = False
if USE_THREADING:
from multiprocessing.dummy import Pool
else:
from multiprocessing.pool import Pool
def worker(start, end):
start_time = time.time()
for n in range(start, end):
arg = f'{n:04}' if start == 0 else {'guess': n}
answer = requests.post('https://www.guessthepin.com/prg.php', data=arg)
if "Holy Moley!" not in str(answer.text):
print("The pin is not", n)
continue
print(f"THE PIN IS: {n}")
end_time = time.time()
print(f"Time taken: {(end_time - start_time) / 60} minutes")
return True
return False
if __name__ == "__main__":
start_time = time.time()
pool = Pool(4)
def task_completion(result):
if result is True:
# One of the functions has terminated having founf the string:
pool.terminate()
pool.apply_async(worker, args=(1000, 4000), callback=task_completion)
pool.apply_async(worker, args=(4000, 7000), callback=task_completion)
pool.apply_async(worker, args=(7000, 10000), callback=task_completion)
pool.apply_async(worker, args=(0, 1000), callback=task_completion)
# Wait for submitted tasks to complete
pool.close()
pool.join()
print("Done!")
end_time = time.time()
print(f"Time taken: {(end_time - start_time)/60} minutes")
проблема в том, что, во-первых, он не выполняет всю функцию, и если ни одно из чисел в функции не является выводом, она не работает. Он выполняет только функцию номер 1. Во-вторых, я выбрал многопроцессорность, потому что она быстрее, и я могу использовать 4 процессора одновременно, но это сильно замедляет ее. Например, если бы я запустил все свои функции, это заняло бы 25 минут, но когда я запустил только одну функцию, это заняло бы 25 минут.
Смотрите обновление к ответу.
См. Что мне делать, если кто-то отвечает на мой вопрос?. Вам следует рассмотреть возможность принятия ответа.
извини, я новичок в stackoverflow
Это не проблема. И принятие ответа не является обязательным.
Вам нужно будет отправить сигнал, например, с помощью
multiprocessing.Event
. Все дочерние процессы должны проверять, установлено ли событие или нет, перед началом следующей итерации и завершать работу, если событие установлено.