2016-06-14 33 views
2

私は、Webサイトを介してクロールし、それが持つすべてのビデオをダウンロードするプログラムを作成しようとしています。私は個々のビデオのダウンロードが完了した後でもスレッドの数が連続的に増加するという問題に直面しています。Pythonでスレッドを終了する

ここには、個々のWorkerオブジェクトのコードがあります。このオブジェクトはキューに入れられ、後で結合されます。これは、スレッドを生成するコードの唯一の部分です。私が理解していないのは、オブジェクトが与えられてもスレッドが残っている可能性があるということです。私はself.stop()関数を実装し、whileループは中断します。

class Worker(Thread): 
def __init__(self, thread_pool): 
    Thread.__init__(self) 
    self.tasks = thread_pool.tasks 
    self.tasks_info = thread_pool.tasks_info 
    self.daemon = True 
    self._is_running=True 

    self.start()   
def stop(self): 
    self._is_running = False 
def run(self): 
    while self._is_running: 
     func, args, kargs = self.tasks.get() 
     try: func(*args, **kargs) 
     except Exception: 
      print("\nError: Threadpool error.") 
      sys.exit(1) 

     self.tasks_info['num_tasks_complete'] += 1    
     self.tasks.task_done() 
     self.stop() 

私が生きているどのスレッドをチェックするスレッド関数を使用しました、そしてそれは私がどのように知っているしない、それは確かにほとんどが労働者の機能だけでなく、Thread(SockThread)_MainThreadと呼ばれる他のオブジェクトであることが判明閉じる。

なぜ、ワーカースレッドが終了していないのか、そして、Thread(SockThread)_MainThreadを取り除く方法を教えてください。

ありがとうございました!

あなたが初期化されているように見えるあなたを見ることによって編集1

class ThreadPool: 
def __init__(self, name, num_threads, num_tasks): 

    self.tasks = Queue(num_threads) 

    self.num_threads=num_threads 
    self.tasks_info = { 
     'name': name, 
     'num_tasks': num_tasks, 
     'num_tasks_complete': 0 
    } 
    for _ in range(num_threads): 
     Worker(self) 
    print(threading.active_count) 


def add_task(self, func, *args, **kwargs): 
    self.tasks.put((func, args, kwargs)) 
def wait_completion(self): 
    print("at the beginning of wait_completion:") 
    print(threading.active_count()) 
+1

あなたは '_MainThread'を取り除きたくありません。つまり、その名前が示すように、インタプリタによって起動された '_MainThread'です。 'func'が実際に何をしているのか分からずにスレッドが止まらない理由を推測するのはかなり難しいです。また、ワーカースレッドの作成方法を知っておくと便利です。 – ig0774

+0

ああ、私はそのスレッドを維持しなければならないか分からなかった。ありがとうございました。ワーカースレッドの作成方法に関するコードの編集1を確認できますか? – Peter

+0

'concurrent.futures.ThreadPoolExecutor'または' multiprocessing.dummy.Pool'(どちらもスレッドに基づいており、別々のプロセスではありません)を使用していない理由は何ですか? – ShadowRanger

答えて

0

あなたも正しい方法ではありませんstartメソッドを使用してprocessing.afterためにrun()メソッドを呼び出しますthread.which 。 以下のコードを使用してください。

 

from threading import Event 
class Worker(Thread): 
    def __init__(self, thread_pool): 
     self.tasks = thread_pool.tasks 
     self.tasks_info = thread_pool.tasks_info 
     self.exit = Event() 
     super(Thread,self).__init__() 

    def shutdown(self): 
     self.exit.set() 

    def run(self): 
     while not self.exit.is_set(): 
      func, args, kargs = self.tasks.get() 
      try: 
       func(*args, **kargs) 
      except Exception: 
       print("\nError: Threadpool error.") 
       # use shutdown method for error 
       self.shutdown() 
       sys.exit(1) 

      self.tasks_info['num_tasks_complete'] += 1    
      self.tasks.task_done() 
      self.shutdown() 
 
+0

こんにちは、ありがとうございました。私はこれをやろうとしましたが、操作(実行すべきもの)がキューに入れられているキューの.join()メソッドでコード全体が機能しなくなりました(エラーは発生せず、ただ停止します)。これはなぜでしょうか? – Peter

+0

私はuaの機能が何をしているのか分かっていれば、それはガドでしょうか?スレッドを停止しているwhileループの中でシャットダウンを呼び出すことがあります。シャットダウンを使用してプログラムを終了します。 –

関連する問題