복붙노트

[PYTHON] 쓰레드를 죽일 방법이 있습니까?

PYTHON

쓰레드를 죽일 방법이 있습니까?

플래그 / 세마포어 / etc를 설정 / 점검하지 않고 실행중인 스레드를 종료 할 수 있습니까?

해결법

  1. ==============================

    1.일반적으로 파이썬과 어떤 언어로든 스레드를 갑자기 죽이는 것은 나쁜 패턴입니다. 다음과 같은 경우를 생각해보십시오.

    일반적으로 파이썬과 어떤 언어로든 스레드를 갑자기 죽이는 것은 나쁜 패턴입니다. 다음과 같은 경우를 생각해보십시오.

    이것을 처리 할 수있는 좋은 방법은 (자신의 스레드를 관리하는 경우) 각 스레드가 정기적 인 간격으로 검사하여 exit 시간을 확인하는 exit_request 플래그를 갖는 것입니다.

    예 :

    import threading
    
    class StoppableThread(threading.Thread):
        """Thread class with a stop() method. The thread itself has to check
        regularly for the stopped() condition."""
    
        def __init__(self):
            super(StoppableThread, self).__init__()
            self._stop_event = threading.Event()
    
        def stop(self):
            self._stop_event.set()
    
        def stopped(self):
            return self._stop_event.is_set()
    

    이 코드에서는 스레드를 종료 할 때 스레드에서 stop ()을 호출하고 join ()을 사용하여 스레드가 올바르게 종료 될 때까지 기다려야합니다. 스레드는 정기적 인 간격으로 중지 플래그를 확인해야합니다.

    그러나 실제로 스레드를 죽일 필요가있는 경우가 있습니다. 예를 들어, 긴 호출에 대해 사용 중이며이를 인터럽트하려고하는 외부 라이브러리를 랩 할 때입니다.

    다음 코드는 Python 스레드에서 예외를 발생시킬 수 있습니다 (일부 제한 사항 포함).

    def _async_raise(tid, exctype):
        '''Raises an exception in the threads with id tid'''
        if not inspect.isclass(exctype):
            raise TypeError("Only types can be raised (not instances)")
        res = ctypes.pythonapi.PyThreadState_SetAsyncExc(ctypes.c_long(tid),
                                                         ctypes.py_object(exctype))
        if res == 0:
            raise ValueError("invalid thread id")
        elif res != 1:
            # "if it returns a number greater than one, you're in trouble,
            # and you should call it again with exc=NULL to revert the effect"
            ctypes.pythonapi.PyThreadState_SetAsyncExc(ctypes.c_long(tid), None)
            raise SystemError("PyThreadState_SetAsyncExc failed")
    
    class ThreadWithExc(threading.Thread):
        '''A thread class that supports raising exception in the thread from
           another thread.
        '''
        def _get_my_tid(self):
            """determines this (self's) thread id
    
            CAREFUL : this function is executed in the context of the caller
            thread, to get the identity of the thread represented by this
            instance.
            """
            if not self.isAlive():
                raise threading.ThreadError("the thread is not active")
    
            # do we have it cached?
            if hasattr(self, "_thread_id"):
                return self._thread_id
    
            # no, look for it in the _active dict
            for tid, tobj in threading._active.items():
                if tobj is self:
                    self._thread_id = tid
                    return tid
    
            # TODO: in python 2.6, there's a simpler way to do : self.ident
    
            raise AssertionError("could not determine the thread's id")
    
        def raiseExc(self, exctype):
            """Raises the given exception type in the context of this thread.
    
            If the thread is busy in a system call (time.sleep(),
            socket.accept(), ...), the exception is simply ignored.
    
            If you are sure that your exception should terminate the thread,
            one way to ensure that it works is:
    
                t = ThreadWithExc( ... )
                ...
                t.raiseExc( SomeException )
                while t.isAlive():
                    time.sleep( 0.1 )
                    t.raiseExc( SomeException )
    
            If the exception is to be caught by the thread, you need a way to
            check that your thread has caught it.
    
            CAREFUL : this function is executed in the context of the
            caller thread, to raise an excpetion in the context of the
            thread represented by this instance.
            """
            _async_raise( self._get_my_tid(), exctype )
    

    (Tomer Filiba의 Killable Threads 기반 PyThreadState_SetAsyncExc의 반환 값에 대한 인용문은 이전 버전의 Python에서 나온 것 같습니다.)

    문서에서 언급했듯이 스레드가 파이썬 인터프리터 외부에서 사용 중이면 인터럽트를 catch하지 않기 때문에 이것은 불가사의 한 사항은 아닙니다.

    이 코드의 좋은 사용 패턴은 스레드가 특정 예외를 catch하고 정리를 수행하도록하는 것입니다. 그렇게하면 작업을 중단하고 적절한 정리 작업을 수행 할 수 있습니다.

  2. ==============================

    2.이를 수행하는 공식 API는 없습니다.

    이를 수행하는 공식 API는 없습니다.

    스레드를 죽이기 위해 플랫폼 API를 사용해야합니다 (예 : pthread_kill 또는 TerminateThread. 예 : API에 액세스 할 수 있습니다. pythonwin을 통해, 또는 ctypes를 통해.

    이것은 본질적으로 안전하지 않다는 점에 유의하십시오. 쓰레기가되는 스택 프레임의 로컬 변수에서 수집 할 수없는 쓰레기가 발생할 가능성이 높아지며, 죽을 때 쓰레드가 죽는 시점에 GIL이 있으면 교착 상태가 발생할 수 있습니다.

  3. ==============================

    3.다중 처리. 프로세스는 p.terminate ()

    다중 처리. 프로세스는 p.terminate ()

    쓰레드를 죽이고 싶지만 플래그 / 잠금 / 시그널 / 세마포어 / 이벤트 / 어떤 것을 사용하고 싶지 않은 경우, 나는 쓰레드를 완전히 날려 버린다. 단지 몇 개의 스레드를 사용하는 코드의 경우 오버 헤드가 그렇게 나쁘지 않습니다.

    예 : 이것은 blocking I / O를 실행하는 helper "threads"를 쉽게 종료 할 수 있도록 도와줍니다

    변환은 간단합니다 : 관련 코드에서 모든 threading.Thread를 다중 처리로 바꿉니다. 프로세스 및 모든 queue.Queue with multiprocessing.Queue 및 p.terminate ()의 필수 호출을 자식 p를 죽이려는 부모 프로세스에 추가하십시오.

    파이썬 문서

  4. ==============================

    4.전체 프로그램을 종료하려는 경우 스레드를 "데몬"으로 설정할 수 있습니다. 만나다 Thread.daemon

    전체 프로그램을 종료하려는 경우 스레드를 "데몬"으로 설정할 수 있습니다. 만나다 Thread.daemon

  5. ==============================

    5.스레드와 협력하지 않고 스레드를 강제로 종료하지 마십시오.

    스레드와 협력하지 않고 스레드를 강제로 종료하지 마십시오.

    쓰레드를 죽이면 try / finally 블록이 설정된다는 보장이 없어 지므로 잠금을 잠그고 파일을 열어 둘 수 있습니다.

    강제로 스레드를 강제 종료하는 것이 좋은 생각이라고 주장 할 수있는 유일한 시간은 프로그램을 빠르게 종료하지만 결코 단일 스레드를 종료하지 않는 것입니다.

  6. ==============================

    6.이것은 thread2 - 킬 가능 스레드 (Python recipe)를 기반으로합니다.

    이것은 thread2 - 킬 가능 스레드 (Python recipe)를 기반으로합니다.

    ctypes를 통해서만 사용할 수있는 PyThreadState_SetasyncExc ()를 호출해야합니다.

    이것은 Python 2.7.3에서만 테스트되었지만 최근의 다른 2.x 릴리즈에서도 작동 할 가능성이 높습니다.

    import ctypes
    
    def terminate_thread(thread):
        """Terminates a python thread from another thread.
    
        :param thread: a threading.Thread instance
        """
        if not thread.isAlive():
            return
    
        exc = ctypes.py_object(SystemExit)
        res = ctypes.pythonapi.PyThreadState_SetAsyncExc(
            ctypes.c_long(thread.ident), exc)
        if res == 0:
            raise ValueError("nonexistent thread id")
        elif res > 1:
            # """if it returns a number greater than one, you're in trouble,
            # and you should call it again with exc=NULL to revert the effect"""
            ctypes.pythonapi.PyThreadState_SetAsyncExc(thread.ident, None)
            raise SystemError("PyThreadState_SetAsyncExc failed")
    
  7. ==============================

    7.다른 사람들이 언급했듯이, 표준은 정지 플래그를 설정하는 것입니다. 경량 (Thread의 서브 클래 싱이 없으며 전역 변수가 없음)의 경우 람다 콜백이 옵션입니다. stop () 인 경우 괄호에 유의하십시오.

    다른 사람들이 언급했듯이, 표준은 정지 플래그를 설정하는 것입니다. 경량 (Thread의 서브 클래 싱이 없으며 전역 변수가 없음)의 경우 람다 콜백이 옵션입니다. stop () 인 경우 괄호에 유의하십시오.

    import threading
    import time
    
    def do_work(id, stop):
        print("I am thread", id)
        while True:
            print("I am thread {} doing something".format(id))
            if stop():
                print("  Exiting loop.")
                break
        print("Thread {}, signing off".format(id))
    
    
    def main():
        stop_threads = False
        workers = []
        for id in range(0,3):
            tmp = threading.Thread(target=do_work, args=(id, lambda: stop_threads))
            workers.append(tmp)
            tmp.start()
        time.sleep(3)
        print('main: done sleeping; time to stop the threads.')
        stop_threads = True
        for worker in workers:
            worker.join()
        print('Finis.')
    
    if __name__ == '__main__':
        main()
    

    print ()를 항상 flushes (sys.stdout.flush ())하는 pr () 함수로 바꾸면 쉘 출력의 정밀도가 향상 될 수 있습니다.

    (Windows / Eclipse / Python3.3에서만 테스트되었습니다)

  8. ==============================

    8.파이썬에서는 단순히 스레드를 직접 죽일 수 없습니다.

    파이썬에서는 단순히 스레드를 직접 죽일 수 없습니다.

    실제로 쓰레드 (!)를 가질 필요가 없다면 쓰레딩 패키지를 사용하는 대신 할 수있는 일은 다중 처리 패키지. 여기, 프로세스를 죽이기 위해서, 당신은 간단하게 메소드를 호출 할 수있다 :

    yourProcess.terminate()  # kill the process!
    

    파이썬은 당신의 프로세스를 죽일 것이다 (유닉스에서 SIGTERM 시그널을 통해, 윈도우즈에서는 TerminateProcess ()를 통해). 대기열이나 파이프를 사용하는 동안주의를 기울이십시오! (대기열 / 파이프의 데이터가 손상 될 수 있음)

    multiprocessing.Event 및 multiprocessing.Semaphore는 threading.Event 및 threading.Semaphore와 동일한 방식으로 정확하게 작동합니다. 실제로, 첫번째 것들은 고리의 클론입니다.

    정말로 스레드를 사용해야하는 경우 직접 스레드를 죽일 방법이 없습니다. 그러나 할 수있는 일은 "데몬 스레드"를 사용하는 것입니다. 사실, 파이썬에서 스레드는 데몬으로 플래그 될 수 있습니다 :

    yourThread.daemon = True  # set the Thread as a "daemon thread"
    

    살아 있지 않은 비 데몬 스레드가 남아 있지 않으면 주 프로그램이 종료됩니다. 즉, 주 스레드 (물론 데몬이 아닌 스레드)가 작업을 완료하면 여전히 일부 데몬 스레드가 작동하더라도 프로그램이 종료됩니다.

    start () 메서드가 호출되기 전에 스레드를 데몬으로 설정해야합니다!

    물론 멀티 프로세싱을 사용하는 경우에도 데몬을 사용할 수 있고 사용해야합니다. 여기에서 주 프로세스가 종료되면 모든 주요 프로세스의 자식 프로세스를 종료하려고 시도합니다.

    마지막으로, sys.exit () 및 os.kill ()은 선택 사항이 아니라는 점에 유의하십시오.

  9. ==============================

    9.스레드를 종료 할 스레드에 추적을 설치하여 스레드를 종료 할 수 있습니다. 가능한 구현을 위해 첨부 된 링크를 참조하십시오.

    스레드를 종료 할 스레드에 추적을 설치하여 스레드를 종료 할 수 있습니다. 가능한 구현을 위해 첨부 된 링크를 참조하십시오.

    파이썬에서 스레드 죽이기

  10. ==============================

    10.스레드를 죽이지 않는 것이 좋습니다. 스레드의 사이클에 "try"블록을 삽입하고 스레드를 중지하려는 경우 예외를 throw하는 방법이있을 수 있습니다 (예 : for / while / ...을 중지시키는 break / return / ...). 내 애플 리케이션에 이것을 사용하고 그것은 작동 ...

    스레드를 죽이지 않는 것이 좋습니다. 스레드의 사이클에 "try"블록을 삽입하고 스레드를 중지하려는 경우 예외를 throw하는 방법이있을 수 있습니다 (예 : for / while / ...을 중지시키는 break / return / ...). 내 애플 리케이션에 이것을 사용하고 그것은 작동 ...

  11. ==============================

    11.다음 예제 코드와 같이 Thread.stop 메서드를 구현할 수 있습니다.

    다음 예제 코드와 같이 Thread.stop 메서드를 구현할 수 있습니다.

    import sys
    import threading
    import time
    
    
    class StopThread(StopIteration):
        pass
    
    threading.SystemExit = SystemExit, StopThread
    
    
    class Thread2(threading.Thread):
    
        def stop(self):
            self.__stop = True
    
        def _bootstrap(self):
            if threading._trace_hook is not None:
                raise ValueError('Cannot run thread with tracing!')
            self.__stop = False
            sys.settrace(self.__trace)
            super()._bootstrap()
    
        def __trace(self, frame, event, arg):
            if self.__stop:
                raise StopThread()
            return self.__trace
    
    
    class Thread3(threading.Thread):
    
        def _bootstrap(self, stop_thread=False):
            def stop():
                nonlocal stop_thread
                stop_thread = True
            self.stop = stop
    
            def tracer(*_):
                if stop_thread:
                    raise StopThread()
                return tracer
            sys.settrace(tracer)
            super()._bootstrap()
    
    ###############################################################################
    
    
    def main():
        test1 = Thread2(target=printer)
        test1.start()
        time.sleep(1)
        test1.stop()
        test1.join()
        test2 = Thread2(target=speed_test)
        test2.start()
        time.sleep(1)
        test2.stop()
        test2.join()
        test3 = Thread3(target=speed_test)
        test3.start()
        time.sleep(1)
        test3.stop()
        test3.join()
    
    
    def printer():
        while True:
            print(time.time() % 1)
            time.sleep(0.1)
    
    
    def speed_test(count=0):
        try:
            while True:
                count += 1
        except StopThread:
            print('Count =', count)
    
    if __name__ == '__main__':
        main()
    

    Thread3 클래스는 Thread2 클래스보다 약 33 % 빠른 코드를 실행하는 것으로 보입니다.

  12. ==============================

    12.

    from ctypes import *
    pthread = cdll.LoadLibrary("libpthread-2.15.so")
    pthread.pthread_cancel(c_ulong(t.ident))
    

    t는 당신의 Thread 객체이다.

    파이썬 소스 (모듈 / threadmodule.c 및 파이썬 / thread_pthread.h)를 보면 Thread.ident가 pthread_t 유형이라는 것을 알 수 있으므로 pthread가 파이썬에서 libpthread를 사용하여 할 수있는 모든 작업을 수행 할 수 있습니다.

  13. ==============================

    13.한 가지 추가하고자하는 것은 lib Python을 스레딩 할 때 공식 문서를 읽는다면 Paolo Rovelli가 언급 한 플래그로 스레드가 갑자기 종료되는 것을 원하지 않을 때 "악마"스레드를 사용하지 않는 것이 좋습니다.

    한 가지 추가하고자하는 것은 lib Python을 스레딩 할 때 공식 문서를 읽는다면 Paolo Rovelli가 언급 한 플래그로 스레드가 갑자기 종료되는 것을 원하지 않을 때 "악마"스레드를 사용하지 않는 것이 좋습니다.

    공식 문서에서 :

    데몬 스레드를 만드는 것은 응용 프로그램에 달려 있다고 생각하지만, 일반적으로 (내 의견으로는) 그들을 죽이거나 악마로 만드는 것을 피하는 것이 좋습니다. 다중 처리에서는 is_alive ()를 사용하여 프로세스 상태를 확인하고 "종료"하여 종료 할 수 있습니다 (GIL 문제도 피할 수 있음). 그러나 Windows에서 코드를 실행하면 더 많은 문제가 발생할 수 있습니다.

    그리고 "라이브 스레드"가 있다면 파이썬 인터프리터가 기다려야한다는 것을 기억하십시오. (왜냐하면이 대음 때문에 갑자기 중요하지 않다면 도움이 될 수 있습니다.)

  14. ==============================

    14.나는이 게임에 좀 늦었지만 유사한 질문으로 씨름 해 왔고 다음과 같이이 문제를 완벽하게 해결했다. 그리고 daemonized 서브 스레드가 종료 될 때 몇 가지 기본적인 스레드 상태 검사 및 정리를 수행하게한다.

    나는이 게임에 좀 늦었지만 유사한 질문으로 씨름 해 왔고 다음과 같이이 문제를 완벽하게 해결했다. 그리고 daemonized 서브 스레드가 종료 될 때 몇 가지 기본적인 스레드 상태 검사 및 정리를 수행하게한다.

    import threading
    import time
    import atexit
    
    def do_work():
    
      i = 0
      @atexit.register
      def goodbye():
        print ("'CLEANLY' kill sub-thread with value: %s [THREAD: %s]" %
               (i, threading.currentThread().ident))
    
      while True:
        print i
        i += 1
        time.sleep(1)
    
    t = threading.Thread(target=do_work)
    t.daemon = True
    t.start()
    
    def after_timeout():
      print "KILL MAIN THREAD: %s" % threading.currentThread().ident
      raise SystemExit
    
    threading.Timer(2, after_timeout).start()
    

    수율 :

    0
    1
    KILL MAIN THREAD: 140013208254208
    'CLEANLY' kill sub-thread with value: 2 [THREAD: 140013674317568]
    
  15. ==============================

    15.방법은 다음과 같습니다.

    방법은 다음과 같습니다.

    from threading import *
    
    ...
    
    for thread in enumerate():
        if thread.isAlive():
            try:
                thread._Thread__stop()
            except:
                print(str(thread.getName()) + ' could not be terminated'))
    

    몇 초 후에 스레드를 중지해야합니다. thread._Thread__delete () 메소드도 확인하십시오.

    편의를 위해 thread.quit () 메서드를 사용하는 것이 좋습니다. 예를 들어 스레드에 소켓이있는 경우 socket-handle 클래스에서 quit () 메서드를 만들고 소켓을 종료 한 다음 quit () 내부에서 thread._Thread__stop ()을 실행하는 것이 좋습니다.

  16. ==============================

    16.setDaemon (True)로 서브 스레드를 시작하십시오.

    setDaemon (True)로 서브 스레드를 시작하십시오.

    def bootstrap(_filename):
        mb = ModelBootstrap(filename=_filename) # Has many Daemon threads. All get stopped automatically when main thread is stopped.
    
    t = threading.Thread(target=bootstrap,args=('models.conf',))
    t.setDaemon(False)
    
    while True:
        t.start()
        time.sleep(10) # I am just allowing the sub-thread to run for 10 sec. You can listen on an event to stop execution.
        print('Thread stopped')
        break
    
  17. ==============================

    17.다소 오래되었지만 일부 사용자에게 편리한 솔루션 일 수 있습니다.

    다소 오래되었지만 일부 사용자에게 편리한 솔루션 일 수 있습니다.

    import threading
    import ctypes     
    
    def _async_raise(tid, excobj):
        res = ctypes.pythonapi.PyThreadState_SetAsyncExc(tid, ctypes.py_object(excobj))
        if res == 0:
            raise ValueError("nonexistent thread id")
        elif res > 1:
            # """if it returns a number greater than one, you're in trouble, 
            # and you should call it again with exc=NULL to revert the effect"""
            ctypes.pythonapi.PyThreadState_SetAsyncExc(tid, 0)
            raise SystemError("PyThreadState_SetAsyncExc failed")
    
    class Thread(threading.Thread):
        def raise_exc(self, excobj):
            assert self.isAlive(), "thread must be started"
            for tid, tobj in threading._active.items():
                if tobj is self:
                    _async_raise(tid, excobj)
                    return
    
            # the thread was alive when we entered the loop, but was not found 
            # in the dict, hence it must have been already terminated. should we raise
            # an exception here? silently ignore?
    
        def terminate(self):
            # must raise the SystemExit type, instead of a SystemExit() instance
            # due to a bug in PyThreadState_SetAsyncExc
            self.raise_exc(SystemExit)
    

    따라서 "스레드가 다른 스레드의 컨텍스트에서 예외를 발생시키는"것을 허용하며 종료 된 스레드는 중단 플래그를 정기적으로 확인하지 않고 종료를 처리 할 수 ​​있습니다.

    그러나 원래 소스에 따르면이 코드에는 몇 가지 문제가 있습니다.

  18. ==============================

    18.ØMQ 프로젝트의 창시자 중 한 명인 Pieter Hintjens는 ØMQ를 사용하고 잠금, 뮤텍스, 이벤트 등과 같은 동기화 프리미티브를 피하는 것이 멀티 스레드 프로그램을 작성하는 가장 확실하고 안전한 방법이라고 말합니다.

    ØMQ 프로젝트의 창시자 중 한 명인 Pieter Hintjens는 ØMQ를 사용하고 잠금, 뮤텍스, 이벤트 등과 같은 동기화 프리미티브를 피하는 것이 멀티 스레드 프로그램을 작성하는 가장 확실하고 안전한 방법이라고 말합니다.

    http://zguide.zeromq.org/py:all#Multithreading-with-ZeroMQ

    여기에는 하위 스레드에게 작업을 취소해야 함을 알리는 작업이 포함됩니다. 스레드에 ØMQ 소켓을 설치하고 해당 소켓을 폴링하여 취소해야한다는 메시지를 보내면됩니다.

    링크는 또한 ØMQ가있는 멀티 스레드 파이썬 코드의 예제를 제공합니다.

  19. ==============================

    19.다음 해결 방법을 사용하여 스레드를 종료 할 수 있습니다.

    다음 해결 방법을 사용하여 스레드를 종료 할 수 있습니다.

    kill_threads = False
    
    def doSomething():
        global kill_threads
        while True:
            if kill_threads:
                thread.exit()
            ......
            ......
    
    thread.start_new_thread(doSomething, ())
    

    이것은 코드가 다른 모듈에 쓰여진 스레드를 주 스레드에서 종료하는 경우에도 사용할 수 있습니다. 우리는 해당 모듈에서 전역 변수를 선언하고이를 사용하여 해당 모듈에서 생성 된 스레드 / 스레드를 종료 할 수 있습니다.

    나는 보통 프로그램 종료시 모든 스레드를 종료하기 위해 이것을 사용합니다. 이것은 thread / s를 종료하는 완벽한 방법은 아니지만 도움이 될 수 있습니다.

  20. ==============================

    20.명시 적으로 스레드의 일부로 time.sleep ()을 호출하는 경우 (일부 외부 서비스 폴링) Phillipe의 방법을 개선하면 sleep () 메서드가있는 곳에서 이벤트의 wait () 메서드에서 제한 시간을 사용하는 것이 좋습니다.

    명시 적으로 스레드의 일부로 time.sleep ()을 호출하는 경우 (일부 외부 서비스 폴링) Phillipe의 방법을 개선하면 sleep () 메서드가있는 곳에서 이벤트의 wait () 메서드에서 제한 시간을 사용하는 것이 좋습니다.

    예 :

    import threading
    
    class KillableThread(threading.Thread):
        def __init__(self, sleep_interval=1):
            super().__init__()
            self._kill = threading.Event()
            self._interval = sleep_interval
    
        def run(self):
            while True:
                print("Do Something")
    
                # If no kill signal is set, sleep for the interval,
                # If kill signal comes in while sleeping, immediately
                #  wake up and handle
                is_killed = self._kill.wait(self._interval)
                if is_killed:
                    break
    
            print("Killing Thread")
    
        def kill(self):
            self._kill.set()
    

    그런 다음 그것을 실행

    t = KillableThread(sleep_interval=5)
    t.start()
    # Every 5 seconds it prints:
    #: Do Something
    t.kill()
    #: Killing Thread
    

    sleep () 대신에 wait ()를 사용하고 이벤트를 정기적으로 확인하는 것의 이점은 더 긴 시간의 수면 시간에 프로그래밍 할 수 있다는 것입니다. 스레드는 거의 즉시 중지됩니다 (그렇지 않으면 잠자기 () 될 때). exit 처리를위한 코드는 훨씬 간단합니다.

  21. ==============================

    21.이 목적을 위해 구축 된 도서관이 있습니다. 여기에 나열된 동일한주의 사항 중 일부는 여전히 적용되지만 적어도이 라이브러리는 명시된 목표를 달성하기 위해 정기적 인 반복 가능한 기술을 제공합니다.

    이 목적을 위해 구축 된 도서관이 있습니다. 여기에 나열된 동일한주의 사항 중 일부는 여전히 적용되지만 적어도이 라이브러리는 명시된 목표를 달성하기 위해 정기적 인 반복 가능한 기술을 제공합니다.

  22. ==============================

    22.이것은 Windows 7에서 pywin32와 함께 작동하는 것

    이것은 Windows 7에서 pywin32와 함께 작동하는 것

    my_thread = threading.Thread()
    my_thread.start()
    my_thread._Thread__stop()
    
  23. ==============================

    23.프로세스에서 명령을 실행 한 다음 프로세스 ID를 사용하여 프로세스를 종료 할 수 있습니다. 두 스레드 중 하나가 자체적으로 반환하지 않는 사이에 동기화해야했습니다.

    프로세스에서 명령을 실행 한 다음 프로세스 ID를 사용하여 프로세스를 종료 할 수 있습니다. 두 스레드 중 하나가 자체적으로 반환하지 않는 사이에 동기화해야했습니다.

    processIds = []
    
    def executeRecord(command):
        print(command)
    
        process = subprocess.Popen(command, stdout=subprocess.PIPE)
        processIds.append(process.pid)
        print(processIds[0])
    
        #Command that doesn't return by itself
        process.stdout.read().decode("utf-8")
        return;
    
    
    def recordThread(command, timeOut):
    
        thread = Thread(target=executeRecord, args=(command,))
        thread.start()
        thread.join(timeOut)
    
        os.kill(processIds.pop(), signal.SIGINT)
    
        return;
    
  24. ==============================

    24.실제로 하위 작업을 종료 할 수있는 기능이 필요한 경우 대체 구현을 사용하십시오. 멀티 프로세싱과 gevent는 모두 "스레드"를 무차별로 죽이는 것을 지원합니다.

    실제로 하위 작업을 종료 할 수있는 기능이 필요한 경우 대체 구현을 사용하십시오. 멀티 프로세싱과 gevent는 모두 "스레드"를 무차별로 죽이는 것을 지원합니다.

    파이썬의 스레딩은 취소를 지원하지 않습니다. 시도하지도 마라. 코드가 교착 상태에 빠지거나 메모리가 손상되거나 누출 될 가능성이 높거나 드물지만 비결정 적으로 발생하는 의도하지 않은 "재미있는"어려운 디버그 효과가있을 수 있습니다.

  25. from https://stackoverflow.com/questions/323972/is-there-any-way-to-kill-a-thread by cc-by-sa and MIT license