• Python学习笔记九


    Python学习笔记之九

    为什么要有操作系统

      管理硬件,提供接口。

      管理调度进程,并且将多个进程对硬件的竞争变得有序。

    操作系统发展史

      第一代计算机:真空管和穿孔卡片

             没有操作系统,所有的程序设计直接操控硬件

             优点:程序员独享整个资源

               缺点:浪费资源

      第二代计算机:晶体管和批处理系统

             优点:计算机资源利用

             缺点:程序员共享资源,出现问题,找不出问题,影响开发效率

      第三代计算机:集成电路芯片和多道程序设计

             多道程序:cpu执行程序的过程中遇到I/O,不会原地等待,cpu会去执行其他命令,等到程序执行完I/O.(时间上的复用)

                  实现一个看起来像并发。CPU随时切换进程。会影响CPU执行效率。

                               进程占用一个内存空间,每个进程的内存空间,是隔离的。(空间上的复用)

      第四代计算机:个人计算机

    多道技术:

      产生背景:针对单核,实现并发。

      空间复用:内存空间是隔离的

      时间复用:遇到I/O就切,提高效率

           遇到运行时间过长,不提高效率

             

    并发与并行

      并发:伪并行,单个CPU+多道技术,看起来像同时运行。

      并行:多个CPU才能实现并行

    windows和linux创建进程:

      windows: createprocess创建进程的接口

      linux: fork创建进程的接口

      创建子进程:

        linux:子进程是父进程的完整副本,

        windows:父进程与子进程的内存地址有所不同

        

    进程状态:

      运行

      阻塞:碰到I/O,便要让出CPU让其他进程执行,保证CPU一直在工作。

      就绪:时刻准备着运行

      

    开启进程的两种方式:

      为什么开启子进程就实现了并发?

      开启子进程就为了执行自己的任务,而不会因为父进程阻塞,而影响自己。

    开启子进程的第一种方法:

    from multiprocessing import Process
    import
    time,random def piao (name): print('%s is piaoing' %name) # time.sleep(3000) if __name__ == '__main__': # p=Process(target=piao,args=('alex',)) p=Process(target=piao,kwargs={'name':'alex'}) p.start() #向操作系统发送开启子进程的信号 # p.join() print ('主进程')
    结果:

    "D:\Program Files\Python36\python.exe" C:/Users/yangjianbo/PycharmProjects/untitled/第九课并发编程/开启子进程.py
    主进程
    alex is piaoing

    结论:

    p.start() 只是向操作系统发出一个开启子进程的信号,而不是真正的开启子进程。

    当p.start()执行完以后,会立刻执行下一行代码,也就是print(),而不是等待子进程执行后,再执行print(). 

    p.start()只能执行一次,多次会有报错。

     上面的例子:如果我想要子进程执行完毕以后,再执行print(),如何实现?

    子进程执行完,再执行主进程的代码。

    from multiprocessing import Process
    import time,random
    def piao (name):
          print('%s is piaoing' %name)
          # time.sleep(3000)
    if __name__ == '__main__':
          # p=Process(target=piao,args=('alex',))
          p=Process(target=piao,kwargs={'name':'alex'})
          p.start()     #向操作系统发送开启子进程的信号
          p.join()
          print ('主进程')
    结果:

    "D:\Program Files\Python36\python.exe" C:/Users/yangjianbo/PycharmProjects/untitled/第九课并发编程/开启子进程.py
    alex is piaoing
    主进程

    结论:在p.start()后面添加一个p.join(),主进程就会在当前位置停下,等待子进程运行完成,再执行后面的代码。p.join()必须在p.start()的后面,否则子进程还未开启,p.join()也没有意义。这么做的意义就是为了防止主进程突然关闭,而导致子进程执行完毕以后,成为了僵尸进程。

     开启子进程的第二种方法:

    采用自定义类的方式。

    from multiprocessing import Process
    import time,random
    class Myprocess(Process):
          def __init__(self,name):
                super(Myprocess,self).__init__()
                self.name=name
          def run(self):
                print ('%s is piaoing' %self.name)
    
    if __name__ == '__main__':
        p=Myprocess('alex')
        p.start()
        print('')

    套接字通信开启子进程

    服务端:

    from socket import socket
    from multiprocessing import Process
    def tongxin(conn,addr):
        while True:
            try:
                cmd = conn.recv(1024)  # 收消息,限制单个消息的最大数为1024字节
                if not cmd: break
                conn.send(cmd.upper())
            except ConnectionResetError:
                break
        conn.close()
    def lianjie():
        s = socket()
        s.bind(('127.0.0.1', 8080))  # 插卡,指定服务器的IP地址和端口号
        s.listen(5)
        while True:
            conn, client_addr = s.accept()
            p=Process(target=tongxin,args=(conn,client_addr))
            p.start()
        s.close()
    
    if __name__ == '__main__':
        lianjie()

    客户端:

    import socket
    client=socket.socket(socket.AF_INET,socket.SOCK_STREAM)
    client.connect(('127.0.0.1',8080))      #打电话
    
    while True:
        cmd=input('数据>>').strip()
        if not cmd:continue
        client.send(cmd.encode('utf-8'))    #发消息
        recv=client.recv(1024).decode('gbk')       #收消息
        print(recv)
    
    client.close()

    进程对象的其他方法:

    join方法:

    from multiprocessing import Process
    import time,random
    def piao (name):
          print('%s is piaoing' %name)
    
    if __name__ == '__main__':
          p1=Process(target=piao,args=('alex',))
          p2=Process(target=piao,args=('egon',))
          p3 = Process(target=piao, args=('wupaiqi',))
          p1.start()
          p2.start()
          p3.start()
    
          p1.join()
          p2.join()
          p3.join()
          print ('主进程')
    结果:

    "D:\Program Files\Python36\python.exe" C:/Users/yangjianbo/PycharmProjects/untitled/第九课并发编程/进程的其他对象方法.py
    egon is piaoing
    alex is piaoing
    wupaiqi is piaoing
    主进程

    结论:

    三个start()都是随机开启的,不会按顺序启动的。

    三个join要放在三个start的后面,这样才是并发。

    from multiprocessing import Process
    import time,random
    def piao (name):
          print('%s is piaoing' %name)
    
    if __name__ == '__main__':
          p1=Process(target=piao,args=('alex',))
          p2=Process(target=piao,args=('egon',))
          p3 = Process(target=piao, args=('wupaiqi',))
          p1.start()
          p1.join()
          p2.start()
          p2.join()
          p3.start()
          p3.join()
          # p1.join()
          # p2.join()
          # p3.join()
          print ('主进程')
    结果:

    "D:\Program Files\Python36\python.exe" C:/Users/yangjianbo/PycharmProjects/untitled/第九课并发编程/进程的其他对象方法.py
    alex is piaoing
    egon is piaoing
    wupaiqi is piaoing
    主进程

    结论:

    如果是这么写的,就是真正的串行。

    from multiprocessing import Process
    import time,random
    def piao (name):
          print('%s is piaoing' %name)
    
    if __name__ == '__main__':
          p1=Process(target=piao,args=('alex',))
          p2=Process(target=piao,args=('egon',))
          p3 = Process(target=piao, args=('wupaiqi',))
          p_l=[p1,p2,p3]
          for p in p_l:
              p.start()
          for p in p_l:
              p.join()
          print ('主进程')

    进程之间的内存空间是隔离的

    from multiprocessing import Process
    n=100
    def task():
        global  n
        n=0
        print (n)
    if __name__ == '__main__':
        p=Process(target=task)
        p.start()
        p.join()
        print('',n)
    结果:

    "D:\Program Files\Python36\python.exe" C:/Users/yangjianbo/PycharmProjects/untitled/第九课并发编程/进程之间的内存空间是隔离的.py
    0
    主 100

    结论:

    进程之间的内存空间是隔离的,因为我修改了子进程的n,但是主进程的n还是原来的。

    查看进程的pid和ppid。

    杀死进程

    进程池

                  

            

    一往无前虎山行,拨开云雾见光明
  • 相关阅读:
    面试问题 集锦
    减少 lwip 消耗 的 RAM
    Blocking Master Example QT 自带 的 serial 即 串口 例子
    32位 的变量 用于表示 ms ,可以表示多少天那?
    centos 腾讯云 今天买了 18个月
    Linux BLE 基于 树莓派
    树莓派 4G模块 PPP 拨号 NDIS 拨号
    linux备份还原命令
    centos7中/tmp文件保存天数
    centos7查看可登陆用户
  • 原文地址:https://www.cnblogs.com/yangjianbo/p/7846768.html
Copyright © 2020-2023  润新知