一 . current_thread的用法

  1. import threading
  2. import time
  3. from threading import Thread, current_thread
  4. def func(n):
  5. time.sleep(1)
  6. print('子线程名称', current_thread().getName()) # Thread-1
  7. print(f'{n}号线程任务')
  8. if __name__ == '__main__':
  9. t = Thread(target=func, args=(1,))
  10. t.start()
  11. print('主线程名称',current_thread().getName()) # MainThread
  12. print('主线程ID',current_thread().ident)
  13. print(current_thread()) # 当前运行的进程
  14. print(threading.enumerate()) # 列举正在运行的线程
  15. print(threading.active_count()) # 查看有多少正在运行的线程

二 . 线程队列(重点)

  1. 先进先出(FIFO)队列 (常用)

  1. import queue
  2. # 一:先进先出队列
  3. q = queue.Queue(3) #先进先出 fifo first in first out
  4. q.put(1)
  5. q.put(2)
  6. print('当前队列内容长度',q.qsize())
  7. q.put(3)
  8. print('查看队列是否满了', q.full())
  9. try:
  10. q.put_nowait(4) # 用put_nowait 因为队列是共享的,不确定谁往里面放东西,所以用它试错
  11. except Exception:
  12. print('队列满了')
  13. print(q.get())
  14. print(q.get())
  15. print('查看队列是否为空', q.empty())
  16. print(q.get())
  17. print('查看队列是否为空', q.empty())
  18. try:
  19. q.get_nowait() # queue.Empty
  20. except Exception:
  21. print('队列空了')

  2.先进后出(FILO) (常用)

  1. import queue
  2. # 二 先进后出队列,或者后进先出,类似于栈
  3. q = queue.LifoQueue(3)
  4.  
  5. q.put('乔峰')
  6. q.put('段誉')
  7. q.put('虚竹')
  8.  
  9. print(q.get()) # 虚竹
  10. print(q.get()) # 段誉
  11. print(q.get()) # 乔峰

  3.优先级队列 (不常用)

  1. import queue
  2. #优先级队列
  3. q = queue.PriorityQueue(5)
  4. # 先比较元组前边数字的大小,数字越小优先级越高, -1 < 0 < 1,
  5. # 如果数字相同,比较元元组第二项
  6. q.put((5,'alex'))
  7. q.put((2,'宝宝'))
  8. q.put((7,'大力'))
  9.  
  10. print(q.get()) # (2, '宝宝')
  11. print(q.get()) # (5, 'alex')
  12. print(q.get()) # (7, '大力')

三 . 线程池(重点)

  1. import time
  2. from concurrent.futures import ThreadPoolExecutor, ProcessPoolExecutor
  3. def f1(n,s):
  4. time.sleep(1)
  5. # print(n,s)
  6. return f'{n}号' + s
  7.  
  8. if __name__ == '__main__':
  9. tp = ThreadPoolExecutor(4) # 线程的个数里面的参数 * 5, 不写参数就是cpu核数 * 5
  10. # tp = ProcessPoolExecutor(4) 这个是进程,这个方法比较常用 进程的个数就是参数,不写就是cpu 的核数
  11. # tp.map(f1,range(10)) #异步提交任务(瞬间提交,不执行里面的函数),参数同样是任务名称,可迭代对象
  12. res_list = []
  13. for i in range(10):
  14. # tp.submit(f1,{'段誉':i},'六脉神剑') 不能接返回值,下面的可以
  15. res = tp.submit(f1,i,'乔峰') # submit是给线程池异步提交任务, 里面随便传参
  16. print(res)
  17. res_list.append(res)
  18. tp.shutdown() #主线程等待所有提交给线程池的任务,全部执行完毕 close + join
  19. for r in res_list:
  20. print(r.result()) # 相当于 进程里面的 .get()
  21. print('主线程结束')

四. 协程

  1. 生成器版协程(最low,了解)

  1. import time
  2. def f1():
  3. for i in range(5):
  4. time.sleep(0.5)
  5. print('f1>>',i)
  6. yield
  7. def f2():
  8. g = f1()
  9. for i in range(5):
  10. time.sleep(0.5)
  11. print('f2>>', i)
  12. next(g)
  13. f1()
  14. f2()
  15. # f2 与 f1 交替出值

  2. greenlet版协程(中档,了解)

  1. import time
  2. from greenlet import greenlet
  3. def f1(n):
  4. print('第一次执行f1' + n)
  5. time.sleep(1)
  6. g2.switch('阿朱') # 第一次传参就行 以后的g2.switch() 不用传参
  7. print('第二次执行f1' + n)
  8. g2.switch()
  9. def f2(n):
  10. print('第一次执行f2' + n)
  11. time.sleep(1)
  12. g1.switch()
  13. print('第二次执行f2' + n)
  14. g1 = greenlet(f1) # 实例化一个greenlet对象,并将任务名称作为参数参进去
  15. g2 = greenlet(f2)
  16. g1.switch('乔峰') # 里面可以传参, 执行g1里面的任务

  3. gevent 真正的协程(重点)

  1. from gevent import monkey;monkey.patch_all()
  2. import gevent
  3. import time
  4. def f1():
  5. print('第一次f1')
  6. # gevent.sleep(1)
  7. time.sleep(2)
  8. print('第二次f1')
  9. return 15
  10. def f2():
  11. print('第一次f2')
  12. # gevent.sleep(2)
  13. time.sleep(3)
  14. print('第二次f2')
  15. s = time.time()
  16. g1 = gevent.spawn(f1) # 异步提交了f1任务
  17. g2 = gevent.spawn(f2) # 异步提交了f2任务
  18. gevent.joinall([g1,g2]) # 必须joinall 不然主协程代码执行结束后就结束,不管上面的代码是否执行
  19. e = time.time()
  20. print('执行时间:', e-s)
  21. print('主程序任务')
  22. # 两个gevent模块必须都导入,如果只import gevent模块,那么只有gevent.sleep()这种IO模式可以并发,其他IO不支持并发

  上例gevent.sleep(2)模拟的是gevent可以识别的 IO阻塞. 而time.sleep(2)或者是其他的阻塞, gevent是不能直接识别的, 需要用下面的一段代码, 打补丁, 就可以识别了. from gevent import monkey;monkey.patch_all, 这段代码必须放在被打补丁者的前面,如time, socket模块之前. (只要用到gevent 就直接写在最前面把)

五 . 线程池回调函数

  1. from concurrent.futures import ThreadPoolExecutor,ProcessPoolExecutor
  2. def f1(n,s):
  3. return n+s
  4. def f2(n):
  5. print('回调函数>>>', n.result()) # 回调函数>>> 23
  6. if __name__ == '__main__':
  7. tp = ThreadPoolExecutor(4)
  8. res = tp.submit(f1, 11, 12).add_done_callback(f2)

  

python之路--线程的其他方法的更多相关文章

  1. python之路----线程

    线程概念的引入背景 进程 程序并不能单独运行,只有将程序装载到内存中,系统为它分配资源才能运行,而这种执行的程序就称之为进程.程序和进程的区别就在于:程序是指令的集合,它是进程运行的静态描述文本:进程 ...

  2. Python之路——线程池

    1 线程基础 1.1 线程状态 线程有5种状态,状态转换的过程如下图所示: 1.2 线程同步——锁 多线程的优势在于可以同时运行多个任务(至少感觉起来是这样,其实Python中是伪多线程).但是当线程 ...

  3. python之路 线程、进程、协程、队列、python-memcache、python-redis

    一.线程 Threading用于提供线程相关的操作,线程是应用程序中工作的最小单元. #!/usr/bin/env python # -*- coding:utf-8 -*- import threa ...

  4. python 并发和线程

    并发和线程 基本概念 - 并行.并发 并行, parallel 互不干扰的在同一时刻做多件事; 如,同一时刻,同时有多辆车在多条车道上跑,即同时发生的概念. 并发, concurrency 同时做某些 ...

  5. Python之路(第四十六篇)多种方法实现python线程池(threadpool模块\multiprocessing.dummy模块\concurrent.futures模块)

    一.线程池 很久(python2.6)之前python没有官方的线程池模块,只有第三方的threadpool模块, 之后再python2.6加入了multiprocessing.dummy 作为可以使 ...

  6. Python之路(第四十二篇)线程相关的其他方法、join()、Thread类的start()和run()方法的区别、守护线程

    一.线程相关的其他方法 Thread实例对象的方法 # isAlive(): 返回线程是否活动的. # getName(): 返回线程名. # setName(): 设置线程名. ​ threadin ...

  7. Python之路【第七篇】:线程、进程和协程

    Python之路[第七篇]:线程.进程和协程   Python线程 Threading用于提供线程相关的操作,线程是应用程序中工作的最小单元. 1 2 3 4 5 6 7 8 9 10 11 12 1 ...

  8. Python之路,Day9, 进程、线程、协程篇

    本节内容 操作系统发展史介绍 进程.与线程区别 python GIL全局解释器锁 线程 语法 join 线程锁之Lock\Rlock\信号量 将线程变为守护进程 Event事件 queue队列 生产者 ...

  9. Python之路,进程、线程、协程篇

      本节内容 进程.与线程区别 cpu运行原理 python GIL全局解释器锁 线程 语法 join 线程锁之Lock\Rlock\信号量 将线程变为守护进程 Event事件 queue队列 生产者 ...

随机推荐

  1. Python 带参数的装饰器 [2] 函数参数类型检查

    在Python中,不知道函数参数类型是一个很正常的事情,特别是在一个大项目里.我见过有些项目里,每一个函数体的前十几行都在检查参数类型,这实在是太麻烦了.而且一旦参数有改动,这部分也需要改动.下面我们 ...

  2. CF817F MEX Queries

    嘟嘟嘟 这题一直在我的某谷任务计划里,不知为啥一直没做. 现在看起来很水啊,就是离散化+线段树.可能是当时没想明白怎么离散化吧. 就是先把算有区间端点都离线下来,然后把\(l - 1, l, l + ...

  3. iptables 从一台机到另一台机端口转发

    启用网卡转发功能#echo 1 > /proc/sys/net/ipv4/ip_forward 举例:从192.168.0.132:21521(新端口)访问192.168.0.211:1521端 ...

  4. Python:Day41 http、css

    HTTP(hypertext transport protocol),即超文本传输协议.这个协议详细规定了浏览器和万维网服务器之间互相通信的规则. 2.请求协议 请求协议的格式如下: 请求首行: // ...

  5. Troubleshooting ORA-12547 TNS: Lost Contact (Doc ID 555565.1)

    Troubleshooting ORA-12547 TNS: Lost Contact (Doc ID 555565.1) This error can occur in following scen ...

  6. Spring Security(十四):5.4 Authorize Requests

    Our examples have only required users to be authenticated and have done so for every URL in our appl ...

  7. Node.js读取某个目录下的所有文件夹名字并将其写入到json文件

    针对解决的问题是,有些时候我们需要读取某个文件并将其写入到对应的json文件(xml文件也行,不过目前用json很多,json是主流). 源码如下:index.js var fs = require( ...

  8. P1171 售货员的难题--搜索(剪枝)

    题目背景 数据有更改 题目描述 某乡有nn个村庄(1<n \le 201<n≤20),有一个售货员,他要到各个村庄去售货,各村庄之间的路程s(0<s<1000)s(0<s ...

  9. 环境部署(四):Linux下查看JDK安装路径

    在安装好Git.JDK和jenkins之后,就需要在jenkins中进行对应的设置,比如在全局工具配置模块,需要写入JDK的安装路径. 这篇博客,介绍几种常见的在Linux中查看JDK路径的方法... ...

  10. RabbitMQ详解(一)------简介与安装

    RabbitMQ 这个消息中间件,其实公司最近的项目中有用到,但是一直没有系统的整理,最近看完了<RabbitMQ实战  高效部署分布式消息队列>这本书,所以顺便写写. 那么关于 Rabb ...