Страница 1 из 2 12 ПоследняяПоследняя
Показано с 1 по 10 из 12

Тема: Как в Python threading thread stop thread?

  1. Как в Python threading thread stop thread?

    Разбираюсь с потоками в Python и столкнулся с проблемой остановки треда. Есть у кого примеры или советы по корректной остановке потока? Не хочу использовать устаревшие или потенциально опасные способы. Посоветуйте, как грамотно и безопасно это сделать?



  2. Ждём вас в нашем чате в Телеграмм ==>> @pythoneer_chat

    А ТАКЖЕ: Канал о Python, статьи и книги ==>>
    @pythoneer_ru

  3. В Python остановка тредов не такая тривиальная задача. Тут нельзя просто взять и убить поток, как это делается в некоторых языках. Рекомендую использовать флаг для завершения.
    Пример:
    Программный код:
    import threading
    import time

    class StoppableThread(threading.Thread):
        
    def __init__(self):
            
    super().__init__()
            
    self._stop_event threading.Event()

        
    def run(self):
            while 
    not self._stop_event.is_set():
                print(
    "Работаю")
                
    time.sleep(1)

        
    def stop(self):
            
    self._stop_event.set()

    StoppableThread()
    t.start()
    time.sleep(5)  # Поток работает 5 сек
    t.stop()  # Останавливаем поток
    t.join() 
    Сразу понятно, что это делает код: пересекаем Event flag при остановке.

    Надеюсь, помог!

  4. Цитата Сообщение от mahastiy
    В Python остановка тредов не такая тривиальная задача. Тут нельзя просто взять и убить поток, как это делается в некоторых языках. Рекомендую использовать флаг для завершения.
    Пример:
    Программный код:
    import threading
    import time

    class StoppableThread(threading.Thread):
        
    def __init__(self):
            
    super().__init__()
            
    self._stop_event threading.Event()

        
    def run(self):
            while 
    not self._stop_event.is_set():
                print(
    "Работаю")
                
    time.sleep(1)

        
    def stop(self):
            
    self._stop_event.set()

    StoppableThread()
    t.start()
    time.sleep(5)  # Поток работает 5 сек
    t.stop()  # Останавливаем поток
    t.join() 
    Сразу понятно, что это делает код: пересекаем Event flag при остановке.

    Надеюсь, помог!
    Кстати, использование Event объекта действительно лучше, чем убивать поток силами ОС. Продолжай в том же духе!

  5. Самый простой способ - это использование глобального флага. Правда, тут могут возникнуть гонки данных, поэтому все аккуратно нужно.

    Программный код:
    import threading
    import time

    stop_thread 
    False

    def thread_function
    ():
        global 
    stop_thread
        
    while not stop_thread:
            print(
    "Работаю")
            
    time.sleep(1)

    threading.Thread(target=thread_function)
    t.start()
    time.sleep(5)  # Поток работает 5 сек
    stop_thread True  # Флаг остановки
    t.join() 
    Это, конечно, не лучший вариант, но быстро и грязно работает.

  6. Цитата Сообщение от Frodo
    Самый простой способ - это использование глобального флага. Правда, тут могут возникнуть гонки данных, поэтому все аккуратно нужно.

    Программный код:
    import threading
    import time

    stop_thread 
    False

    def thread_function
    ():
        global 
    stop_thread
        
    while not stop_thread:
            print(
    "Работаю")
            
    time.sleep(1)

    threading.Thread(target=thread_function)
    t.start()
    time.sleep(5)  # Поток работает 5 сек
    stop_thread True  # Флаг остановки
    t.join() 
    Это, конечно, не лучший вариант, но быстро и грязно работает.
    Грубо, но эффективно. Гонка данных все равно может поджидать, так что поаккуратнее с этим.

  7. Честно говоря, правильный способ завязывать на Event или использовать какой-нибудь безопасный подход как Pyro.

    Но если ты хочешь понимания, как работает останавливаемость потоков, вот еще один пример:

    Программный код:
    import threading

    class MyThread(threading.Thread):
        
    def __init__(selfstop_event):
            
    super().__init__()
            
    self.stop_event stop_event

        def run
    (self):
            while 
    not self.stop_event.is_set():
                
    # Выполняй какие-то действия
                
    pass

    stop_event 
    threading.Event()
    thread MyThread(stop_event)
    thread.start()

    # Когда нужно остановить
    stop_event.set()
    thread.join() 

  8. Цитата Сообщение от Iceman
    Честно говоря, правильный способ завязывать на Event или использовать какой-нибудь безопасный подход как Pyro.

    Но если ты хочешь понимания, как работает останавливаемость потоков, вот еще один пример:

    Программный код:
    import threading

    class MyThread(threading.Thread):
        
    def __init__(selfstop_event):
            
    super().__init__()
            
    self.stop_event stop_event

        def run
    (self):
            while 
    not self.stop_event.is_set():
                
    # Выполняй какие-то действия
                
    pass

    stop_event 
    threading.Event()
    thread MyThread(stop_event)
    thread.start()

    # Когда нужно остановить
    stop_event.set()
    thread.join() 
    Нормальный вариант, упреждает всякие гонки данных. Суть дела в синхронизации потоков.

  9. Если рассматривать более advanced подходы, можно подключать thread pools или другие библиотеки управления потоками, например, concurrent.futures. Но для простых кейсов флагоформат нормально.

    Программный код:
    import concurrent.futures
    import time

    def thread_function
    (stop_event):
        while 
    not stop_event.is_set():
            print(
    "Работаю")
            
    time.sleep(1)

    stop_event threading.Event()
    with concurrent.futures.ThreadPoolExecutor(max_workers=1) as executor:
        
    future executor.submit(thread_functionstop_event)
        
    time.sleep(5)  # Поток работает 5 сек
        
    stop_event.set()
        
    future.result() 
    Немного сложнее, но гибче.

  10. Цитата Сообщение от Страж
    Если рассматривать более advanced подходы, можно подключать thread pools или другие библиотеки управления потоками, например, concurrent.futures. Но для простых кейсов флагоформат нормально.

    Программный код:
    import concurrent.futures
    import time

    def thread_function
    (stop_event):
        while 
    not stop_event.is_set():
            print(
    "Работаю")
            
    time.sleep(1)

    stop_event threading.Event()
    with concurrent.futures.ThreadPoolExecutor(max_workers=1) as executor:
        
    future executor.submit(thread_functionstop_event)
        
    time.sleep(5)  # Поток работает 5 сек
        
    stop_event.set()
        
    future.result() 
    Немного сложнее, но гибче.
    Да, concurrent.futures модулирует больше гибкости для control, но не забывай и про простоту.

Страница 1 из 2 12 ПоследняяПоследняя