zoukankan      html  css  js  c++  java
  • PYTHON2.day07

    前情回顾

    1. multiprocessing模块 创建进程
       
        基本创建进程: Process(target,args,kwargs,name)
                       start()
               join([timeout])
       
        进程对象属性:p.name  p.pid  p.daemon  p.is_alive()

       自定义进程类:1. 继承Process,重写__init__
                      2. 重写run方法

       进程池: 大量进程事件需要较多进程处理,
                 此时进程池可以避免进程频繁创建销毁带来的系统消耗。

            Pool()  创建进程池对象
             apply_async()  将事件使用进程池执行,async(异步)
             close()  关闭进程池,不能再添加新的事件了
             join()  回收进程池
             map()  使用迭代对象为指定函数传参后,加入进程池

           
    2. 进程间通信
     
        【1】管道  : Pipe()   fd.recv()  fd.send()

       【2】消息队列:Queue()  q.get()获取消息  q.put() 存入消息
                       q.full() q.empty() q.qsize()  q.close()

      1 import os
      2 from multiprocessing import Process
      3 
      4 filename = './he.jpg'
      5 
      6 #获取文件大小
      7 size = os.path.getsize(filename)
      8 
      9 #复制上半部分
     10 def top():
     11     f = open(filename,'rb')
     12     n = size // 2
     13     fw = open("half_top.jpg",'wb')
     14     while True:
     15         if n < 1024:
     16             data = f.read(n)
     17             fw.write(data)
     18             break
     19         data = f.read(1024)
     20         fw.write(data)
     21         n -=1024
     22     f.close()
     23     fw.close()
     24 
     25 #复制下半部分
     26 def boot():
     27     f = open(filename,'rb')
     28     fw = open('half_bottom.jpg','wb')
     29     f.seek(size//2,0)
     30 
     31     while True:
     32         data = f.read(1024)
     33         if not data:
     34             break
     35         fw.write(data)
     36     f.close()
     37     fw.close()
     38 
     39 t = Process(target = top)
     40 b = Process(target = boot)
     41 t.start()
     42 b.start()
     43 t.join()
     44 b.join()
    cope_file.py


    ************************************************************************************************************
    一.进程间通信(续)
    1.共享内存
       【1】通信原理:在内存中开辟一块空间,进程可以写入内容和读取内容完成通信,
                      但是每次写入内容会覆盖之前的内容
       【2】实现方法:
                     from multiprocessing import Value,Array
                    
                     obj = Value(ctype,data)
                     功能:开辟共享内存
                     参数:ctype 表示共享内存空间类型'i'整  'f'浮点  'c'字符
                           data 共享内存空间初始数据

                     返回值:共享内存对象
                    
                    obj.value  对该属性的修改或查看即对共享内存的读写
                    
                     obj = Array(ctype,data)
                     功能:开辟共享内存空间
                     参数:ctype 表示共享内存数据类型
                           data  整数      则表示开辟空间的大小,
                                 其他数据  开辟空间存放的初始化数据

                     返回值:共享内存对象
                    
                    Array共享内存读写:通过遍历obj可以得到的每个值,直接可以通过索引号修改任意值。
         

      1 from multiprocessing import Process,Value
      2 import time
      3 import random
      4 
      5 #创共享内存
      6 money = Value('i',5000)
      7 
      8 #操作共享内存
      9 def man():
     10     for i in range(30):
     11         time.sleep(0.2)
     12         money.value += random.randint(1,1000)
     13 
     14 def girl():
     15     for i in range(30):
     16         time.sleep(0.16)
     17         money.value -= random.randint(100,900)
     18 
     19 m = Process(target=man)
     20 g = Process(target=girl)
     21 m.start()
     22 g.start()
     23 m.join()
     24 g.join()
     25 
     26 print("一月余额:",money.value)
    value.py

    1value     

      1 from multiprocessing import Process,Array
      2 import time
      3 
      4 #创建共享内存
      5 #shm = Array('i',[1,2,3,4,5])
      6 
      7 #创建共享内存,指定开辟空间大小
      8 # shm =Array('i',6)
      9 
     10 
     11 #存如字符串
     12 shm = Array('c',b'Hello')
     13 
     14 
     15 def fun():
     16     for i in shm:
     17         print(i)
     18     # shm[2]=3000
     19     shm[0] = b'h'
     20 
     21 p = Process(target = fun)
     22 p.start()
     23 p.join()
     24 
     25 for i in shm:
     26     print(i,end=" ")
     27 print(shm.value)#打印字符串
    array_2.py

    2array    

      1 from multiprocessing import Process,Array
      2 import time
      3 
      4 #创建共享内存
      5 #shm = Array('i',[1,2,3,4,5])
      6 
      7 #创建共享内存,指定开辟空间大小
      8 # shm =Array('i',6)
      9 
     10 
     11 #存如字符串
     12 shm = Array('c',b'Hello')
     13 
     14 
     15 def fun():
     16     for i in shm:
     17         print(i)
     18     # shm[2]=3000
     19     shm[0] = b'h'
     20 
     21 p = Process(target = fun)
     22 p.start()
     23 p.join()
     24 
     25 for i in shm:
     26     print(i,end=" ")
     27 print(shm.value)#打印字符串
    array_3.py

    2array_3

      1 from multiprocessing import Process,Array
      2 import time
      3 
      4 
      5 #创建共享内存,指定开辟空间大小
      6 shm =Array('i',6)
      7 
      8 
      9 
     10 def fun():
     11     for i in shm:
     12         print(i)
     13     shm[2]=3000
     14 
     15 
     16 p = Process(target = fun)
     17 p.start()
     18 p.join()
     19 
     20 for i in shm:
     21     print(i,end=" ")
     22 print()
    Array.py

    2.信号量(信号灯集)
       [1]通信原理:给定一个数量对多个进程可见。多个进程都可以操作该数量增减,并根据数量决定自己的行为
       [2]实现方法
                 from multiprocessing import Semaphore
                
                 sem = Semaphore(num)

                 功能:创建信号量对象
                 参数:信号量的初始值
                 返回值:信号量对象
                 sem.acqire() 将信号量减1 当信号量为0时阻塞
                 sem.release() 将信号量+1
                 sem.get_value()获取信号量数量

                

    补充:当在父进程中创建套接字,进程间通信对象,文件对象,子进程从父进程获取这些对象时,那么对对象的操作
           会有属性的相互关联影响。如果在各自进程中单独创建这些对象,则各自互不影响。   
        

      1 from multiprocessing import Semaphore,Process
      2 from time import sleep
      3 import os
      4 #创建信号量
      5 sem = Semaphore(3)
      6 
      7 def fun():
      8     print("%d 想执行事件"%os.getpid())
      9     #想执行事件必须得到信号资源
     10     sem.acquire()
     11     print("%s 抢到了一个信号量,可以执行操作"%os.getpid())
     12     sleep(3)
     13     print("%d执行完事件再增加信号量"%os.getgid())
     14     sem.release()
     15 jobs=[]
     16 for i in range(5):
     17     p = Process(target = fun)
     18     jobs.append(p)
     19     p.start()
     20 
     21 for i in jobs:
     22     i.join()
     23 
     24 print(sem.get_value())
    3sem.py

    3
    二.线程编程(Thread)
         1.什么是线程
           【1】线程被称为轻量级的进程
           【2】线程也可以使用计算机多核资源,是多任务编程方式
           【3】线程是系统分配内核的最小单元
           【4】线程可以理解为进程的分支任务
           
           
         2.线程特征
           【1】一个进程中可以包含多个线程
           【2】线程也是一个运行行为,消耗计算机资源
           【3】一个进程中的所有线程共享这个进程的资源
           【4】多个线程之间的运行互不影响各自运行
           【5】线程的创建和销毁消耗资源远小于进程
           【6】各个线程有自己的ID等特征
          
         3.创建线程threading模块
             【1】创建线程对象
                from threading import Thread
                 t = Thread()

                 功能:创建线程对象
                 参数:target 绑定线程对象
                       args   元组 给线程函数位置传参
                       kwargs 字典 给线程函数键值传参

             【2】启动线程
                 t.start()
             【3】回收线程
                t.join([timeout])
                
         4.线程对象属性:
            t.name 线程名称
            t.setName()   设置线程名称
             t.getName()   获取线程名称
            
             t.is_alive()  查看线程是否在生命周期
            
             t.daemon 设置主线程和分支线程的  关系
            t.setDaemon() 设置daemon属性值
             t.isDaemon() 查看daemon属性值
             *daemon为True时主线程退出分支线程也退出。
                    要在start前设置,通常不和join一起使用

      1 import threading
      2 from time import sleep
      3 import os
      4 
      5 a=1
      6 #线程函数
      7 def music():
      8     global a
      9     print("a=",a)
     10     for i in range(5):
     11         sleep(2)
     12         print("播放鱼",os.getpid())
     13         a = 10000
     14 
     15 #创建线程对象
     16 t = threading.Thread(target = music)
     17 t.start()
     18 
     19 #主线程运行任务
     20 for i in range(3):
     21     sleep(3)
     22     print("《大哥》",os.getpid())
     23 t.join()
     24 print("Main thread a:",a)
    thread_1.py

    4.1

      1 from threading import Thread
      2 from time import sleep
      3 
      4 #含有参数的线程函数
      5 def fun(sec,name):
      6     print("线程函数传参")
      7     sleep(sec)
      8     print("%s 线程执行完毕"%name)
      9 
     10 #创建多个线程
     11 threads = []
     12 for i in range(5):
     13     t = Thread(target = fun,args=(2,),kwargs={'name':'T%d'%i})
     14     threads.append(t)
     15     t.start()
     16 
     17 for i in threads:
     18     i.join()
    thread_2.py

    4thread2

      1 from threading import Thread
      2 from time import sleep
      3 
      4 def fun():
      5     sleep(3)
      6     print("线程属性测试")
      7 
      8 # t = Thread(target = fun)
      9 t = Thread(target = fun,name = 'Tarena')
     10 
     11 
     12 
     13 #线程名称
     14 t.setName('Tedu')#设置完会覆盖之间前的名称
     15 print('Thread name:',t.name)
     16 print("Thread name:",t.getName())
     17 
     18 
     19 #设置daemon为True
     20 t.setDaemon(True)
     21 t.start()
     22 
     23 #查看线程的生命周期
     24 print("alive:",t.is_alive())
     25 t.join()
    thread_attr.py

    4thread_attr
         5.自定义线程类:
             【1】创建步骤
                 1. 继承Thread类
                 2.重写__init__方法添加自己的属性,使用super加载父类属性
                 3.重写run方法
             【2】使用方法
                 1.实例化对象
                 2.调用start自动执行run方法
                 3.调用join回收线程
         

      1 from threading import Thread
      2 from time import sleep,ctime
      3 
      4 class MyThread(Thread):
      5     def __init__(self,target=None,args=(),kwargs={},name='Tedu'):
      6         super().__init__()
      7         self.target = target
      8         self.args = args
      9         self.kwargs = kwargs
     10         self.name = name
     11 
     12     def run(self):
     13         self.target(*self.args,**self.kwargs)
     14 def player(sec,song):
     15     for i in range(2):
     16         print("playing %s:%s"%(song,ctime()))
     17         sleep(sec)
     18 
     19 t = MyThread(target = player,args=(3,),kwargs={'song':'凉凉'},name='happy')
     20 
     21 t.start()
     22 t.join()
    mythread.py

    5mythread      
    三.线程通信
         【1】通信方法:线程间使用全局变量间进行通信
         【2】共享资源争夺
                 1.共享资源:多个进程或者线程都可以操作的资源成为公共资源,
                             对共享资源的操作代码段称为临界区。
                 2.影响:对共享资源的而无需操作可能会代来数据的混乱,或者操作错误。
                        此时往往需要同步互斥机制协调操作顺序。
         【3】同步互斥机制
              同步:同步是一种协作关系,为完成操作,多进程或者线程间形成一种协调,
                    按照必要的步骤有序执行操作。
              互斥:是一种制约关系资源,当一个进程或者线程占有资源是会进行加锁处理,
                    此时其他进程线程就无法操作该资源,直到解锁后才能操作。
                
         【4】线程同步互斥方法
             1.线程Event
                 from threading import Event
                 e = Event() 创建线程event对象
                 e.wait([timeout]) 阻塞等待e被set
                 e.set()  设置e,使wait结束阻塞
                 e.clear() 使e回到未被设置的状态
                 e.is_set()查看当前e是否被设置

      1 	from threading import Event
      2 
      3 #创建事件对象
      4 e = Event()
      5 
      6 e.set()#设置e
      7 e.clear()#清楚set状态
      8 print(e.is_set())#查看是否被设置
      9 e.wait(3)#超时时间
     10 print("-------------")
    event_test.py
      1 from threading import Thread,Event
      2 from time import sleep
      3 
      4 s = None#全局变量,用于通信
      5 e = Event()
      6 
      7 def foo():
      8     sleep(0.1)
      9     print("Foo 前来拜山头")
     10     global s
     11     s = "天王盖地虎"
     12     e.set()#设置e
     13 
     14 f = Thread(target = foo)
     15 f.start()
     16 
     17 #主线程验证口令
     18 print("说对口令为自己人")
     19 e.wait()#添加阻塞
     20 if s == '天王盖地虎':
     21     print("是自己人")
     22 else:
     23     print("不是自己人")
     24 
     25 f.join()
    theard_event.py

             2.线程锁 Lock
                 from threading import Lock
                 lock = Lock()#创建锁对象
                 lock.acqire()#上锁 如果lock已经上锁在调用会阻塞
                 lock.release()#解锁
                
                 with lock:   上锁
                    ...
                    ...
                
                           with代码块结束自动解锁   
       
      1 from threading import Thread,Lock
      2 
      3 a = b = 0
      4 lock = Lock()#锁对象
      5 #一个线程
      6 def value():
      7     while True:
      8         lock.acquire()
      9         if a!=b:
     10             print("a=%d,b=%d"%(a,b))
     11         lock.release()
     12 
     13 t = Thread(target=value)
     14 t.start()
     15 #另一个线程
     16 while True:
     17     while True:
     18         with lock:
     19             a +=1
     20             b +=1
     21 
     22 t.join()
    theard_lock.py
      
    作业:1.对比进程线程的特点区别
           2.做单进程,    多进程,           多线程的效率测试 
               执行10遍    创建10个进程      创建10个线程
                           每个执行一遍      每个执行一遍

  • 相关阅读:
    [币严区块链]数字货币交易所之比特币(BTC)钱包对接 | 自建节点JSON-RPC访问
    [币严区块链]以太坊(ETH)Dapp开发入门教程之宠物商店领养游戏
    一句话的设计模式
    在线捉鬼游戏开发
    华容道程序求解
    利用多态,实现一般处理程序(ashx)中的AOP(切面编程)
    客户端-服务器端互动比较与原生实例(比较ajax,server-sent event,websocket/netsocket)
    在线捉鬼游戏开发之三
    在线捉鬼游戏开发之三
    在线捉鬼游戏开发之三
  • 原文地址:https://www.cnblogs.com/shengjia/p/10416284.html
Copyright © 2011-2022 走看看