1

以下の例では、プログラムを複数回実行すると、毎回新しいIDで新しいスレッドが生成されます。1.タスクの完了時にすべてのスレッドを終了するにはどうすればよいですか?2.スレッドに名前/IDを割り当てるにはどうすればよいですか?

import threading, Queue 

THREAD_LIMIT = 3                 
jobs = Queue.Queue(5)           # This sets up the queue object to use 5 slots 
singlelock = threading.Lock()   # This is a lock so threads don't print trough each other 

# list  
inputlist_Values = [ (5,5),(10,4),(78,5),(87,2),(65,4),(10,10),(65,2),(88,95),(44,55),(33,3) ] 

def DoWork(inputlist): 
    print "Inputlist received..."
    print inputlist 

    # Spawn the threads 
    print "Spawning the {0} threads.".format(THREAD_LIMIT) 
    for x in xrange(THREAD_LIMIT): 
        print "Thread {0} started.".format(x) 
        # This is the thread class that we instantiate. 
        worker().start() 

    # Put stuff in queue 
    print "Putting stuff in queue"
    for i in inputlist: 
        # Block if queue is full, and wait 5 seconds. After 5s raise Queue Full error. 
        try: 
            jobs.put(i, block=True, timeout=5) 
        except: 
            singlelock.acquire() 
            print "The queue is full !"
            singlelock.release() 

    # Wait for the threads to finish 
    singlelock.acquire()        # Acquire the lock so we can print 
    print "Waiting for threads to finish."
    singlelock.release()        # Release the lock 
    jobs.join()                 # This command waits for all threads to finish. 

class worker(threading.Thread): 
    def run(self): 
        # run forever 
        while 1: 
            # Try and get a job out of the queue 
            try: 
                job = jobs.get(True,1) 
                singlelock.acquire()        # Acquire the lock 
                print self
                print "Multiplication of {0} with {1} gives {2}".format(job[0],job[1],(job[0]*job[1]))         
                singlelock.release()        # Release the lock 
                # Let the queue know the job is finished. 
                jobs.task_done() 
            except: 
                break           # No more jobs in the queue 


def main():    
    DoWork(inputlist_Values)
4

2 に答える 2

1

タスクの完了時にすべてのスレッドを終了するにはどうすればよいですか?

THREAD_LIMIT番兵の値(たとえばNone)をキューの最後に置きrun()、スレッドがそれを認識した場合はスレッドのメソッドを終了することができます。

メインスレッド出口では、デーモン以外のすべてのスレッドが結合されるため、いずれかのスレッドが稼働している場合でもプログラムは実行を継続します。デーモンスレッドは、プログラムの終了時に終了します。

スレッドに名前/IDを割り当てるにはどうすればよいですか?

名前をコンストラクターに渡すか、.name直接変更することで、名前を割り当てることができます。

スレッド識別子.identは、生きているスレッド間で一意の読み取り専用プロパティです。1つのスレッドが終了し、別のスレッドが開始した場合に再利用される可能性があります。


プロセスの代わりにスレッドを使用multiprocessing.dummy.Poolするのと同じインターフェイスを提供するコードを使用して、コードを書き直すことができます。multiprocessing.Pool

#!/usr/bin/env python
import logging
from multiprocessing.dummy import Pool

debug = logging.getLogger(__name__).debug

def work(x_y):
    try:
        x, y = x_y # do some work here
        debug('got %r', x_y)
        return x / y, None
    except Exception as e:
        logging.getLogger(__name__).exception('work%r failed', x_y) 
        return None, e

def main():
    logging.basicConfig(level=logging.DEBUG,
        format="%(levelname)s:%(threadName)s:%(asctime)s %(message)s")

    inputlist = [ (5,5),(10,4),(78,5),(87,2),(65,4),(10,10), (1,0), (0,1) ]
    pool = Pool(3)
    s = 0.
    for result, error in pool.imap_unordered(work, inputlist):
        if error is None:
           s += result
    print("sum=%s" % (s,))
    pool.close()
    pool.join()

if __name__ == "__main__":
   main()

出力

DEBUG:Thread-1:2013-01-14 15:37:37,253 got (5, 5)
DEBUG:Thread-1:2013-01-14 15:37:37,253 got (87, 2)
DEBUG:Thread-1:2013-01-14 15:37:37,253 got (65, 4)
DEBUG:Thread-1:2013-01-14 15:37:37,254 got (10, 10)
DEBUG:Thread-1:2013-01-14 15:37:37,254 got (1, 0)
ERROR:Thread-1:2013-01-14 15:37:37,254 work(1, 0) failed
Traceback (most recent call last):
  File "prog.py", line 11, in work
    return x / y, None
ZeroDivisionError: integer division or modulo by zero
DEBUG:Thread-1:2013-01-14 15:37:37,254 got (0, 1)
DEBUG:Thread-3:2013-01-14 15:37:37,253 got (10, 4)
DEBUG:Thread-2:2013-01-14 15:37:37,253 got (78, 5)
sum=78.0
于 2013-01-11T03:40:45.150 に答える
0

停止するように指示しない限り、スレッドは停止しません。

サブクラスにstop変数を追加し、この変数が(ではなく)実行ループにあるかどうかを確認することをお勧めします。ThreadTruewhile 1:

例:

class worker(threading.Thread): 
    def __init__(self):
         self._stop = False

    def stop(self):
         self._stop = True

    def run(self): 
        # run until stopped 
        while not self._stop:                 
            # do work

次に、プログラムが(何らかの理由で)終了するときは、stopすべての作業スレッドでメソッドを呼び出す必要があります。

name2番目の質問について、サブクラスに変数を追加しても効果はありませんThreadか?

于 2013-01-11T00:08:06.800 に答える