Python3 ThreadPoolExecutor线程池
用到的模块:concurrent.futures
为什么需要线程池
主线程中可以获取某一个线程的状态或者某一个任务的状态,以及返回值。
futures可以让多线程和多进程编码接口一致
怎么使用
线程池的基类是concurrent.futures模块中的Executor,Executor提供了两个子类,即 ThreadPoolExecutor 和 ProcessPoolExecutor,其中 ThreadPoolExecutor 用于创建线程池,而 ProcessPoolExecutor 用于创建进程池。
如果使用线程池/进程池来管理并发编程,那么只要将相应的 task 函数提交给线程池/进程池,剩下的事情就由线程池/进程池来搞定。
Exectuor 提供了如下常用方法:
- submit(fn, *args, **kwargs):将 fn 函数提交给线程池。*args 代表传给 fn 函数的参数,*kwargs 代表以关键字参数的形式为 fn 函数传入参数。
- map(func, *iterables, timeout=None, chunksize=1):该函数类似于全局函数 map(func, *iterables),只是该函数将会启动多个线程,以异步方式立即对 iterables 执行 map 处理。
- shutdown(wait=True):关闭线程池。
程序将 task 函数提交(submit)给线程池后,submit 方法会返回一个 Future 对象,Future 对象类主要用于获取线程任务函数的返回值。由于是异步任务,Python 用 Future 对象来作为 task 的返回容器。
Future 未来对象
Futrure 提供了以下方法:
class Future(object):
"""Represents the result of an asynchronous computation."""
def __init__(self):
"""Initializes the future. Should not be called by clients."""
self._condition = threading.Condition() # 这里使用了threading中的条件变量 控制线程间同步
self._state = PENDING # 初始状态为待办
self._result = None # 运行结果
self._exception = None # 发生的异常
self._waiters = []
self._done_callbacks = [] # 回调函数集
-
cancel():取消该 Future 代表的线程任务。如果该任务正在执行或者已完成,不可取消,则该方法返回 False;否则,程序会取消该任务,并返回 True。
def cancel(self): """Cancel the future if possible. Returns True if the future was cancelled, False otherwise. A future cannot be cancelled if it is running or has already completed. """ with self._condition: if self._state in [RUNNING, FINISHED]: # return False if self._state in [CANCELLED, CANCELLED_AND_NOTIFIED]: # return True self._state = CANCELLED self._condition.notify_all() self._invoke_callbacks() return True
-
cancelled():返回 Future 代表的线程任务是否被成功取消。
def cancelled(self): """Return True if the future was cancelled.""" with self._condition: return self._state in [CANCELLED, CANCELLED_AND_NOTIFIED]
-
running():如果该 Future 代表的线程任务正在执行、不可被取消,该方法返回 True。
def running(self): """Return True if the future is currently executing.""" with self._condition: return self._state == RUNNING
-
done():如果该 Funture 代表的线程任务被成功取消或执行完成,则该方法返回 True。
def done(self): """Return True of the future was cancelled or finished executing.""" with self._condition: return self._state in [CANCELLED, CANCELLED_AND_NOTIFIED, FINISHED]
-
result(timeout=None):获取该 Future 代表的线程任务最后返回的结果。如果 Future 代表的线程任务还未完成,该方法将会阻塞当前线程,其中 timeout 参数指定最多阻塞多少秒。
def result(self, timeout=None): """Return the result of the call that the future represents. Args: timeout: The number of seconds to wait for the result if the future isn't done. If None, then there is no limit on the wait time. Returns: The result of the call that the future represents. Raises: CancelledError: If the future was cancelled. TimeoutError: If the future didn't finish executing before the given timeout. Exception: If the call raised then that exception will be raised. """ with self._condition: if self._state in [CANCELLED, CANCELLED_AND_NOTIFIED]: raise CancelledError() elif self._state == FINISHED: return self.__get_result() self._condition.wait(timeout) # 阻塞 获取结果 if self._state in [CANCELLED, CANCELLED_AND_NOTIFIED]: