【Python编程】ThreadPoolExecutor 全面指北(2)ThreadPoolExecutor类详解

admin 2023年3月9日08:27:35评论38 views字数 2678阅读8分55秒阅读模式

【Python编程】ThreadPoolExecutor 全面指北(2)ThreadPoolExecutor类详解



0x01  ThreadPoolExecutor类


    concurrent.futures是python3.2提出新的标准库,该模块提供了线程池和进程池,这里我们主要讨论的是线程池。

    如果对并发如何实现感兴趣,可以看下它的源代码

    ThreadPoolExecutor类继承了抽象类Executor,实例化返回的是future对象。


0x02  Executor抽象类


   Executor类定义了三种方法,用来控制线程池:submit()、map()、shutdown()。

    • submit():分发要执行的函数并且返回future对象

    • map():将函数应用于可迭代的元素

    • shutdown():关闭

    map()函数和python内置函数 map(func, iterables)差不多,但不同的是,func 是异步执行的,对 func 的多个调用可以并发执行

    正常来说,Executor创建后就需要调用shutdown()来释放资源,但我们使用with来声明Executor保证线程能被及时关闭,不需要再调用shutdown()。


0x03  Future对象

  

    在计算机科学中,future是指用于在某些并发编程语言中同步程序执行的构造。由于某些计算(或者网络请求)尚未结束,我们需要一个对象来表示这个未知的结果,于是就有了这些构造(future、promise等)。future, promise, delay, deferred可以互相使用。

    在python里,future对象表示异步任务延迟的最终的结果,Future对象当调用submit()的返回。

    Future对象有一些函数,用于检查任务状态:- cancel(): 正在执行的和执行完成的任务不能被取消,返回False,反之则取消任务,返回Ture。- cancelled():如果在任务执行前被取消,返回True。- running():如果任务正在执行,返回 True 。- done():如果任务已被取消或正常结束,返回 True。

    也有一些函数,用于获取结果和异常。- result():获取任务结果。- exception():获取任务执行抛出的异常。

    result()和exception()都可以传参timeout=,单位是秒。如果没有指定timeout或者为None时,则会一直等待。如果在timeout秒期间没有拿到结果,则抛出异常concurrent.futures.TimeoutError。

   为了我们在任务完成时就自动调用函数,future提供了回调函数add_done_callback()。- add_done_callback(fn):一旦任务完成或被取消,则立刻调用fn

    在了解Executor和future后,我们来看看ThreadPoolExecutor是怎么来异步执行任务的。

0x04  使用ThreadPoolExecutor进行线程池异步执行


    ThreadPoolExecutor就是要简单易用,简单的一个流程为:

    • 调用构造函数,创建实例,executor = ThreadPoolExecutor()。

    • 用submit(),map()提交任务。

    • 等待任务执行。

    • 用shutdown()关闭线程池(使用with就不需要再手动关闭)。

import requests  from concurrent.futures import ThreadPoolExecutor,as_completed  
hosts = ['https://mp.weixin.qq.com/s/D_ogfYszTH-osotLC0662g', 'https://mp.weixin.qq.com/s/jcDHVU0b7gdOLkoxNKWjmw', 'https://mp.weixin.qq.com/s/QrMvmk3iXYEDzlk4UVRBNg' ] def request(host): resp = requests.get(host, timeout=2) return resp.text
with ThreadPoolExecutor(max_workers=10) as executor: # 创建10个线程的线程池, future_dict = {executor.submit(request, host): host for host in hosts} # 提交len(datas)个任务,任务函数request(),传入参数host,返回future对象的字典 for future in as_completed(future_dict): # 处理完成的任务 try: data = future.result() except Exception as e: host = future_dict[future] # 之前创建的字典,即可获取到future对象对应传的参数host值 print(('{0}, {1}'.format(host, e))) else: print(data)

0x05  参考链接


    - [1] Python官方文档(https://docs.python.org/3/library/concurrent.futures.html)

    - [2] Future官方文档(https://docs.python.org/zh-cn/3/library/concurrent.futures.html?highlight=future#module-concurrent.futures)

    - [3] WIKI future and promise(https://zh.wikipedia.org/wiki/Future%E4%B8%8Epromise)


0x06  免责声明


    本文仅限于技术研究学习,切勿将文中技术细节用作非法用途,如有违者后果自负。



关于我们


“TERRA星环”安全团队正式成立于2020年,是贵州泰若数字科技有限公司旗下以互联网攻防技术研究为目标的安全团队。团队核心成员长期从事渗透测试、代码审计、应急响应等安服工作,多次参与国家、省级攻防演练行动,具备丰富的安服及攻防对抗经验。

团队专注于漏洞挖掘、漏洞研究、红蓝对抗、CTF夺旗、溯源取证、威胁情报、代码审计、逆向分析等研究。对外提供安全评估、安全培训、安全咨询、安全集成、应急响应等服务。


原文始发于微信公众号(TERRA星环安全团队):【Python编程】ThreadPoolExecutor 全面指北(2)ThreadPoolExecutor类详解

  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2023年3月9日08:27:35
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   【Python编程】ThreadPoolExecutor 全面指北(2)ThreadPoolExecutor类详解http://cn-sec.com/archives/1231930.html

发表评论

匿名网友 填写信息