zoukankan      html  css  js  c++  java
  • 网络编程 线程加进程补充

    网络编程,线程,进程"补充"

    1,进程间的通信IPC

    如何时间进程之间通信

    队列:先进先出

    堆栈:先进后出

    利用队列时间进程之间通信

    1,如何创建一个队列:如

    from multiprocessing import Queue
    #full判断这个队列里面的值是否是满的,返回值是布尔值
    #put,往队列添加值
    #get,从队列中取值
    q = Queue(5)#产生一个能存放最大数据的五个队列
    q.put(1)
    q.put(2)
    q.put(3)
    q.put(3)
    q.put(3)
    print(q.full())
    print(q.get())
    print(q.get())
    print(q.get())
    print(q.get())#如果队列中没有值了那么进程不会结束而是在等在哪里
    from multiprocessing import Queue
    q = Queue(5)
    for i in range(5):#for 循环往队列里面存放数据
       q.put(i)
    print(q.get())
    print(q.get())
    print(q.get())
    q.get_nowait()#在队列有数据的情况下,和get取值是一样的但是当这个队列没有数据了 那么直接报错
    print(q.empty())#判断队列是否为空,需要注意的是在并发的时候这个判断的不是很准确,因为在并发的时候可能在有一瞬间队列是没有值的

    2,进程间通信IPC机制


    from multiprocessing import Process ,Queue
    def producer(q):
       q.put("hello SB")
    def consumer(q):
       print(q.get())
    if __name__ == '__main__':
       q = Queue()#创建 一个队列
       p = Process(target=producer,args=(q,))#将创建好的队列当参数传过去
       c = Process(target=consumer,args=(q,))
       p.start()
       c.start()
    """创建两个子进程,一个存 一个取
    """

     

     

    2,生产者消费模型

    生产者模型

    生产者:做包子 生产数据的

    消费者:买包子 处理数据的

    生产数据多,处理出数据 系统会卡

    生产数据少,处理数据多,处理会等待

    解决供需不平衡的问题

    定义一个队列。用来存放固定数量的数据

    生产数据放在队列,处理数据从队列中取

    解决一个生产者和消费者不需要直接打交道,两者都通过队列打交道

    Queue:管道+一个锁 相当于

    JoinableQueue:可以被等待的管道,

    from multiprocessing import Process ,Queue,JoinableQueue
    import random
    import time
    def producer(name,shangpin,q):
       for i in range(5):
           data = f"大厨{name}生产了{shangpin}{i}"
           time.sleep(random.random())#随机时间
           q.put(data)
           print(data)
    def consumer(name,q):
       while True:
           data = q.get()
           if data==None:break
           print(f"{name}吃了{data}")
           time.sleep(random.random())
           q.task_done()#告诉队列你已经从队列中取出一个数据并且处理完毕了
    if __name__ == '__main__':
       q = JoinableQueue()
       p = Process(target=producer,args=("jason","包子",q,))
       p1 = Process(target=producer, args=("tank","鲍鱼",q,))
       s = Process(target=consumer,args=("egon",q))
       s1 = Process(target=consumer, args=("女老师", q))
       p.start()
       p1.start()
       s.daemon =True#设置守护进程
       s1.daemon = True
       s.start()
       s1.start()
       p.join()
       p1.join()
       q.join()#等待队列所有数据全部取出才能结束

     

    1,线程理论

    1,什么是线程

    进程:资源单位

    线程:执行单位

    进程就是创建了一个内存空间,而线程是进程内存空间里面的代码

    注意:每一个进程中都会自带一个线程

    2,为什么要有线程

    开一个进程:

    申请内存空间 耗时

    将代码拷贝到申请的内存空间中,耗时

    开一个线程:

    不需要申请内存空间

    开线程的开销远远小于开进程的开销

    3,如何是使用线程

    开启线程的两种方式

    2,创建线程的两种方式


    from threading import Thread
    import time
    #第一种使用继承
    class Mythread(Thread):
       def __init__(self,name):
           super().__init__()
           self.name = name
       def run(self):
           print(f"{self.name}是个人才")
           time.sleep(2)
           print(f"{self.name}等待了")
    if __name__ == '__main__':
       t = Mythread("杨鑫")
       t.start()
       print("主")

     

    from threading import Thread
    import time
    #第二种方式
    def task(name):
       print(f"{name}是个人才")
       time.sleep(2)
       print(f"{name}等待了")
    if __name__ == '__main__':
       t = Thread(target=task,args=("yangxin",))
       t.start()
       print("主")

    3,线程对象及其他方法

    from threading import Thread ,current_thread,active_count
    import time
    import os
    def task(name):
       print(f"{name}来了")
       print("子程序",current_thread().name)#查询子线程
       print("子程序",os.getpid())#查询子线程的pip号
       time.sleep(2)
       print("我被延迟了")

    if __name__ == '__main__':
       t = Thread(target=task,args=("haha",))
       t1 = Thread(target=task,args=("yangxin",))
       t.start()#开辟一个线程
       t1.start()#开辟一个线程
       t1.join()
       print("查询当前正在活跃的子线程个数",active_count())
       #小的代码执行完线程就开始了
       print("主")
       print("主线程",current_thread().name)
       print("主线程",os.getpid())

    4,守护线程

    from threading import Thread ,current_thread
    def task(i):
       print(current_thread().name)
       time.sleep(i)
       print("GG")
    if __name__ == '__main__':
       t = Thread(target=task,args=(1,))
       t.daemon = True#设置守护线程
       t.start()
       # t.join()#如果不加这个join那么主结束子线程中的GG也无法打印直接跟随着主进程死亡
       print("主")
    """
    主线程的结束也就意味着进程的结束
    主线程必须等待其他非守护线程的结束才能结束
    (意味子线程在运行的时候需要使用进程中的资源,而主线程一旦结束了资源也就销毁了)

     

    5,线程之间通信

    from threading import Thread
    money = 666
    def task():
       global money
       money = 999
    t = Thread(target=task)
    t.start()
    t.join()
    print(money)

     

    6线程互斥锁

    from threading import Thread,Lock
    import time


    n = 100

    def task(mutex):
       global  n
       mutex.acquire()
       tmp = n
       time.sleep(0.1)
       n = tmp - 1
       mutex.release()

    t_list = []
    mutex = Lock()
    for i in range(100):
       t = Thread(target=task,args=(mutex,))
       t.start()
       t_list.append(t)
    for t in t_list:
       t.join()
    print(n)

    练习

    from threading import Thread
    from multiprocessing import Process
    import time
    def foo():
       print(123)
       time.sleep(1)
       print("end123")

    def bar():
       print(456)
       time.sleep(3)
       print("end456")

    if __name__ == '__main__':
       t1=Thread(target=foo)
       t2=Thread(target=bar)
       t1.daemon=True
       t1.start()
       t2.start()
       print("main-------")

     

  • 相关阅读:
    查询避免Unknown column ‘xxx’ in ‘where clause
    Spring依赖循环:The dependencies of some of the beans in the application context form a cycle
    POJ(北京大学)刷题导航
    ACM使用Java提交总是超时的解决方法
    申请了服务器,建立了新博客。 不在用这个了。
    jeecg数据库添加字段后表单的修改
    jeecg普通表和数据字典的关联
    jeecg添加滚动图
    jeecg定时任务的bug记录
    classpath究竟是指哪里?
  • 原文地址:https://www.cnblogs.com/yangxinpython/p/11341997.html
Copyright © 2011-2022 走看看