zoukankan      html  css  js  c++  java
  • python多线程

    昨天在做题的时候遇上了需要多线程来跑的程序,所以今天打算好好地去学习一下多进程

    具体的理论解释在百度上比比皆是,所以这边我也不再复制粘贴

    这里先直接上个程序来解释单线程与多线程

    import time
    
    def test():
        print('wawawawaaw')
        time.sleep(2)
    
    if __name__ == '__main__':
        for i in range(5):
            test()

    运行这段代码可以看到结果是一行一行进行执行的,接着看一下多线程的:

    #coding:utf-8
    import
    threading import time def test(): print('waaawawawa') time.sleep(2) if __name__=='__main__': for i in range(5): t = threading.Thread(target=test) #调用线程,Thread(target=方法名) t.start() #启动

    可以看到五行结果是同时执行完成的,这就是所谓的多线程

    import threading
    
    def main():
        print(threading.active_count())    #查看有几个正在运行的线程
        print(threading.enumerate())       #查看正在运行线程的list
        print(threading.current_thread())  #查看当前的线程变量
        
    if __name__=='__main__':
        main()

    这里还要提一下join()方法,首先还是看两个例子:

    import threading
    import time
    
    def test():
        print('waaawawawa
    ')
        for i in range(5):
            time.sleep(1)
        print('finish
    ')
    
        
    if __name__=='__main__':
        t = threading.Thread(target=test)
        t.start()
        print('all done
    ')

    运行结果:all done并没有出现在finish之后,这说明main函数中的几个语句是同时执行的,要想all done出现在最后,那么就要加上join()

    加上join后的代码:

    import threading
    import time
    
    def test():
        print('waaawawawa
    ')
        for i in range(5):
            time.sleep(1)
        print('finish
    ')
    
        
    if __name__=='__main__':
        t = threading.Thread(target=test)
        t.start()
        t.join()
        print('all done
    ')

    运行结果:all done出现在了最后

    这里的join()的方法的作用就是等待至线程中止,当以上线程执行完毕后再接着执行main函数接下去的代码

    接着就要提一下Queue:线程优先级队列

    #coding:utf-8
    
    import threading
    from queue import Queue
    
    arr = [[1,2,3],[2,3,4],[3,4,5],[4,5,6]]
    def job(l, q):
        for i in range(len(l)):
            l[i] = l[i]**2            #对传入的数组的每个值进行平方
        q.put(l)                      #将传入的l数组放于队列中
            
    def mulT():
        q = Queue()                   #定义队列q
        threads = []                  #定义一个空的线程数组,将来存放下面四个线程 
        for i in range(4):          
            t = threading.Thread(target=job, args=(arr[i], q))    #生成4个线程,参数分别对应arr中的4个数组
            t.start()                                             #开始多线程
            threads.append(t)                                     #将每个线程添加进threads数组
             
        for thread in threads:                                    
            thread.join()                                         #给每个线程都添加join方法
        result = []
        for j in range(4):
            result.append(q.get())                                #将q队列中存放的4个值添加进result
        print(result)
        
    if __name__=='__main__':
        mulT()
        

    这里只是简单的定义了一个队列,并使用了put()、get()的命令

    Queue 模块中的常用方法:

    • Queue.qsize() 返回队列的大小
    • Queue.empty() 如果队列为空,返回True,反之False
    • Queue.full() 如果队列满了,返回True,反之False
    • Queue.full 与 maxsize 大小对应
    • Queue.get([block[, timeout]])获取队列,timeout等待时间
    • Queue.get_nowait() 相当Queue.get(False)
    • Queue.put(item) 写入队列,timeout等待时间
    • Queue.put_nowait(item) 相当Queue.put(item, False)
    • Queue.task_done() 在完成一项工作之后,Queue.task_done()函数向任务已经完成的队列发送一个信号
    • Queue.join() 实际上意味着等到队列为空,再执行别的操作

    最后就是锁的概念了

    还是先看例子:

    import threading
    
    def job1():
        global A
        for i in range(5):
            A += 1
            print('job1',A)
            
            
    def job2():
        global A
        for i in range(5):
            A += 2
            print('job2',A)
        
        
    if __name__=='__main__':
        A = 0
        t1 = threading.Thread(target=job1)
        t2 = threading.Thread(target=job2)
        t1.start()
        t2.start()
        t1.join()
        t2.join()

    在没有锁的情况下进行多线程打印两个不同的计算结果,可以看到,打印的结果还是有点混乱的

    接着我们给两个线程上个锁:

    import threading
    
    def job1():                                   #上锁的方法很简单,首先在相关线程前调用Lock()的方法,接着使用acquire()、release()两个方法来控制上锁的区域
        global A,lock
        lock.acquire()                  
        for i in range(5):
            A += 1
            print('job1',A)
        lock.release()
            
    def job2():
        global A,lock
        lock.acquire()
        for i in range(5):
            A += 2
            print('job2',A)
        lock.release()
        
    if __name__=='__main__':
        lock = threading.Lock()
        A = 0
        t1 = threading.Thread(target=job1)
        t2 = threading.Thread(target=job2)
        t1.start()
        t2.start()
        t1.join()
        t2.join()
        

    上锁以后,这两个进程就不会相互影响

  • 相关阅读:
    解决ssh: connect to host github.com port 22: Connection refused
    sudo/su命令免密执行
    Linux tar.gz、tar、bz2、zip 等解压缩、压缩命令详解
    项目实战——校验文件名和邮箱地址
    项目实战:判断闰年平年并输出某月的天数
    ubuntu软件更新时出现没有Release文件
    项目实战:根据出生日期判断星座
    项目实战--实现淡旺季飞机票打折
    xxx.java:1: 错误: 类xxx是公共的, 应在名为 xxx.java 的文件中声明 public class xxx
    32位int整数范围
  • 原文地址:https://www.cnblogs.com/Ragd0ll/p/8728216.html
Copyright © 2011-2022 走看看