互斥锁 IPC 生产者消费者

import json
import time
import random
import os
from multiprocessing import Process,Lock

mutex=Lock()
# 互斥锁vs join的区别一:
# 互斥锁可以让一部分代码(修改共享数据的代码)串行,而join只能将代码整体串行

def search():
    time.sleep(random.randint(1,3))
    with open(‘db.json‘,‘r‘,encoding=‘utf-8‘) as f:
        dic=json.load(f)
        print(‘%s 剩余票数:%s‘ %(os.getpid(),dic[‘count‘]))

def get():
    with open(‘db.json‘,‘r‘,encoding=‘utf-8‘) as f:
        dic=json.load(f)
    if dic[‘count‘] > 0:
        dic[‘count‘]-=1
        time.sleep(random.randint(1,3))
        with open(‘db.json‘,‘w‘,encoding=‘utf-8‘) as f:
            json.dump(dic,f)
        print(‘%s 购票成功‘ %os.getpid())

def task(lock):
    search()
    lock.acquire()
    get()
    lock.release()

if __name__ == ‘__main__‘:
    for i in range(10):
        p=Process(target=task,args=(mutex,))
        p.start()

互斥锁得自己加锁  锁是一个危险的事  不然成死锁
所以IPC 机制里的Queue就是帮我们自动处理锁的事
用Queue
队列(推荐使用)
创建队列的类
    Queue([maxsize]):创建共享的进程队列,Queue是多进程安全的队列,
    可以使用Queue实现多进程之间的数据传递。
参数介绍:
      maxsize是队列中允许最大项数,省略则无大小限制。
1.队列:队列类似于一条管道,元素先进先出
需要注意的一点是:队列都是在内存中操作,进程退出,队列清空,另外,队列也是一个阻塞的形态
2.队列分类
队列有很多种,但都依赖与模块queue
q.put方法用以插入数据到队列中,put方法还有两个可选参数:blocked和timeout。如果blocked为True(默认值),并且timeout为正值,该方法会阻塞timeout指定的时间,直到该队列有剩余的空间。如果超时,会抛出Queue.Full异常。如果blocked为False,但该Queue已满,会立即抛出Queue.Full异常。
q.get方法可以从队列读取并且删除一个元素。同样,get方法有两个可选参数:blocked和timeout。如果blocked为True(默认值),并且timeout为正值,那么在等待时间内没有取到任何元素,会抛出Queue.Empty异常。如果blocked为False,有两种情况存在,如果Queue有一个值可用,则立即返回该值,否则,如果队列为空,则立即抛出Queue.Empty异常.
  
q.get_nowait():同q.get(False)
q.put_nowait():同q.put(False)
 
q.empty():调用此方法时q为空则返回True,该结果不可靠,比如在返回True的过程中,如果队列中又加入了项目。
q.full():调用此方法时q已满则返回True,该结果不可靠,比如在返回True的过程中,如果队列中的项目被取走。
q.qsize():返回队列中目前项目的正确数量,结果也不可靠,理由同q.empty()和q.full()一样

来自 <http://www.cnblogs.com/haiyan123/p/7429568.html> 

原文地址:https://www.cnblogs.com/maojiang/p/8948329.html

时间: 2024-11-10 13:11:21

互斥锁 IPC 生产者消费者的相关文章

进程,互斥锁,生产者消费者,线程

进程,互斥锁,生产者消费者,线程 一.僵尸进程与孤儿进程 代码演示 ''' 僵尸进程(有坏处): - 在子进程结束后,主进程没有正常结束,子进程的PID不会被回收. 缺点: - 操作系统中PID号是有限的,比如子进程PID号无法正常回收,则会占用PID号. - 资源浪费 - 若PID号满了,则无法创建新的进程. 孤儿进程(没有坏处): - 在子进程没有结束时,主进程没有"正常结束",子进程PID不会被回收. - 操作系统优化机制(孤儿院): 当主进程意外终止,操作系统会检测是否有正在运

开启子进程的两种方式,孤儿进程与僵尸进程,守护进程,互斥锁,IPC机制,生产者与消费者模型

开启子进程的两种方式 # # # 方式一: # from multiprocessing import Process # import time # # def task(x): # print('%s is running' %x) # time.sleep(3) # print('%s is done' %x) # # if __name__ == '__main__': # # Process(target=task,kwargs={'x':'子进程'}) # p=Process(tar

守护进程,互斥锁,IPC,队列,生产者与消费者模型

小知识点:在子进程中不能使用input输入! 一.守护进程 守护进程表示一个进程b 守护另一个进程a 当被守护的进程结束后,那么守护进程b也跟着结束了 应用场景:之所以开子进程,是为了帮助主进程完成某个任务,然而,如果主进程认为自己的事情一旦做完了就没有必要使用子进程了,就可以将子进程设置为守护进程 例如:在运行qq的过程,开启一个进程,用于下载文件,然而文件还没有下载完毕,qq就退出了,下载任务也应该跟随qq的退出而结束. from multiprocessing import Process

35 守护进程 互斥锁 IPC 共享内存 的方式 生产者消费者模型

守护进程 进程:一个正在运行的程序. 主进程创建守护进程: 1.守护进程会在主进程代码执行结束后就终止, 2.守护进程内无法再开启子进程,否则抛出异常. 注意:进程之间是互相独立的,主进程代码运行结束,守护进程随即终止. 例子:from multiprocessing import Processimport time def task(): print('老了....') time.sleep(2) print('睡了一会..') if __name__ == '__main__': prin

Linux多线程实践(5) --Posix信号量与互斥量解决生产者消费者问题

Posix信号量 Posix 信号量 有名信号量 无名信号量 sem_open sem_init sem_close sem_destroy sem_unlink sem_wait sem_post 有名信号量 #include <fcntl.h> /* For O_* constants */ #include <sys/stat.h> /* For mode constants */ #include <semaphore.h> sem_t *sem_open(co

Operating System-进程间互斥的问题-生产者&amp;&amp;消费者引入

之前介绍的几种解决进程间互斥的方案,不管是Peterson方案还是TSL指令的方式,都有一个特点:当一个进程被Block到临界区外面时,被Block的进程会一直处于忙等待的状态,这个不但浪费了CPU资源,还会有一个很坏的副作用.假设两个进程,H,L,H的优先级高,L进程的优先级非常低,CPU的调度规则是只要H处于Ready状态,则开始运行H,问题来了: H处于BLock状态,可能在等待外部资源 L进入了临界区 H处于Ready状态(外部资源满足),L还没有离开临界区 按照调度规则,CPU会Swi

环形缓冲区的设计及其在生产者消费者模式下的使用(并发有锁环形队列)

1.环形缓冲区 缓冲区的好处,就是空间换时间和协调快慢线程.缓冲区可以用很多设计法,这里说一下环形缓冲区的几种设计方案,可以看成是几种环形缓冲区的模式.设计环形缓冲区涉及到几个点,一是超出缓冲区大小的的索引如何处理,二是如何表示缓冲区满和缓冲区空,三是如何入队.出队,四是缓冲区中数据长度如何计算. ps.规定以下所有方案,在缓冲区满时不可再写入数据,缓冲区空时不能读数据 1.1.常规数组环形缓冲区 设缓冲区大小为N,队头out,队尾in,out.in均是下标表示: 初始时,in=out=0 队头

并发无锁之环形队列生产者消费者问题

1.生产者消费者问题 三种关系:生产者--生产者(互斥):消费者-消费者(互斥):生产者--消费者(互斥同步) 两个角色:生产者:消费者 一种生产场所:缓冲区 2.环形队列(缓冲区) 数据结构:可以有多种,这里选用数组,逻辑上将a[0]和a[size-1]相连构成环形队列 判断空/判断满:当读指针和写指针指向同一个区域为空,或者满(但不能区分空或者满) 两种方案:1.即尾结点与首结点之间至少留有一个元素的空间. 2. 添加一个计数器(信号量就是计数器所以这里用信号量完成计数器的功能) 3.sem

jdk线程的生产者消费者问题

同步代码块实现生产者消费者模式 class Person { private String name; private String sex; private Boolean isEmpty = Boolean.TRUE; // 表示存储区域是否为空 //生产 public void set(String name, String sex) { synchronized (this) { // if(isEmpty) while (!isEmpty.equals(Boolean.TRUE)) {