Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/317.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/multithreading/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 线程池等待直到池中的线程可用(节流)_Python_Multithreading_Multiprocessing - Fatal编程技术网

Python 线程池等待直到池中的线程可用(节流)

Python 线程池等待直到池中的线程可用(节流),python,multithreading,multiprocessing,Python,Multithreading,Multiprocessing,我想对线程池中正在处理的大量项目实施节流功能,一次只限制处理(或排队等待执行)的250个项目 pool = ThreadPool(250) def func(i): print(i) time.sleep(3) i = 0 while True: # The amount of items is virtually infinite i+=1 # Block here - if there are no free threads available in t

我想对
线程池
中正在处理的大量项目实施节流功能,一次只限制处理(或排队等待执行)的
250个项目

pool = ThreadPool(250)

def func(i):
    print(i)
    time.sleep(3)

i = 0 
while True: # The amount of items is virtually infinite
    i+=1
    # Block here - if there are no free threads available in the pool
    pool.map_async(func,[i]) # Once delegated, don't block and move forward

如何实现注释中所示的功能?

您可以使用池中的线程数初始化
线程.Semaphore
,然后使用此信号量初始化线程池本身。然后,每个工作线程都会发出信号,表示它已经完成了任务,并通过对信号量发出
release
调用来释放正在运行它的线程,这会增加信号量计数。因此,信号量保持空闲线程数的计数。在向池提交新任务之前,对信号量进行
acquire
调用。如果信号量计数不是正的(至少有一个空闲线程),这将阻塞。否则,信号量计数将减少(现在少了一个空闲线程)

从multiprocessing.pool导入线程池
从线程导入信号量
导入时间
def func(一):
印刷品(一)
时间。睡眠(3)
semaphore.release()#显示此线程现在可用
池大小=10
信号量=信号量(值=池大小)
池=线程池(池大小)
i=0
对于范围(20)内的i:
#此处阻止-如果池中没有可用的可用线程
semaphore.acquire()
"""
#为了证明我们正在阻塞,而不是执行简单的信号量。aquire():
如果semaphore.acquire(blocking=False)为False:
print('我们将阻止i=',i)
semaphore.acquire()#执行实际的阻塞调用
"""
pool.apply_async(func,args=(i,)#一旦委托,不要阻止并向前移动
#等待所有任务完成:
pool.close()
pool.join()
使用回调

从multiprocessing.pool导入线程池
从线程导入信号量
导入时间
def func(一):
印刷品(一)
时间。睡眠(3)
池大小=10
def my_回调(结果):
semaphore.release()#显示此线程现在可用
信号量=信号量(值=池大小)
池=线程池(池大小)
i=0
对于范围(20)内的i:
#此处阻止-如果池中没有可用的可用线程
semaphore.acquire()
"""
#为了证明我们正在阻塞,而不是执行简单的信号量。aquire():
如果semaphore.acquire(blocking=False)为False:
print('我们将阻止i=',i)
semaphore.acquire()#执行实际的阻塞调用
"""
pool.apply_async(func,args=(i,),callback=my_callback)#一旦委托,不要阻止并向前移动
#或:
#pool.apply_async(func,args=(i,),callback=lambda result:semaphore.release())#一旦委托,不要阻止并向前移动
#等待所有任务完成:
pool.close()
pool.join()

工作正常!将
信号量.release
传递到
apply\u async
作为
callback
会更好吗?比如:
pool.apply\u async(work\u func,args=(None,),callback=semaphore.release)
首先我更新了我的答案。我已经习惯于多处理而不是多线程,因为每个进程都有自己的地址空间。在本例中,我不需要池初始值设定项函数来让worker函数对信号量具有可见性。其次,使用回调来释放信号量是一个多么好的主意!但是,您不能按您建议的方式执行,因为无论worker函数返回什么结果,都会传递回调,并且
信号量.acquire
不接受任何参数(按您的方式执行会导致异常)。我提供了一个确实有效的例子。太棒了!在我的例子中,我刚刚使用了
lambda\uz:semaphore.release()
作为回调函数,而不是编写另一个函数。不管怎么说,是信号灯干的!为你干杯,但我不太清楚你为什么要这么做。通常情况下,您可以提交任务,而它们只会坐在队列上等待池中的线程变为空闲线程,一旦线程变为空闲线程,它将很快开始执行。但是,通过这种机制,您会发现一个线程已变得空闲,只有这样,您才能将任务排队执行。因此,在任务开始执行之前,会有稍大的延迟。它还调用像
map
这样的方法,这些方法一次提交多个任务。你不必回答;这只是你要考虑的事情。