当前位置: 首页 > article >正文

python multiprocessing lock锁在相同父进程ID起作用

python多进程之间实现数据共享需要使用queue队列,全局变量不起作用
lock锁在同一个主进程ID下子进程ID之间起作用,不同的主进程ID互不干扰
下面来看代码

import multiprocessing,time,datetime
a=1
def demo1():
    global a
    a+=1
    print('进程1',a,datetime.datetime.now())
def demo2():
    time.sleep(2)
    print('进程2',a,datetime.datetime.now())

def demo3():
    print('开始执行进程3')
    lock.acquire()
    for i in range(5):
        time.sleep(2)
        q.put(i)
    lock.release()
    print('进程3',datetime.datetime.now())
def demo4():
    print('开始执行进程4')
    time.sleep(1)
    while not q.empty():
        print('进程4获取值:',q.get())
    time.sleep(2)
    print('进程4',datetime.datetime.now())

q=multiprocessing.Queue()
lock=multiprocessing.Lock()
multiprocessing.Process(target=demo1).start()
multiprocessing.Process(target=demo2).start()
multiprocessing.Process(target=demo3).start()
multiprocessing.Process(target=demo4).start()

运行结果

(python38) [root@mysql01 dtask]# python 2.py 
开始执行进程3
开始执行进程4
进程1 2 2024-10-25 15:29:38.662167
进程2 1 2024-10-25 15:29:40.662385
进程4 2024-10-25 15:29:41.666102
进程3 2024-10-25 15:29:48.670803

可以看到进程1结果是2 进程2结果是1
进程2还可以延迟,global在这个里面没有起效果
然后进程3和进程4 lock锁只对进程3有作用,并没有对进程4有任何作用,因为进程4无需持有锁,所以不受锁干扰
下面单独写一个进程

import multiprocessing,time,datetime,os

def demo():
    time.sleep(1)
    print('执行时间:',datetime.datetime.now(),f'子进程名字:{multiprocessing.current_process().name},当前进程ID:{os.getpid()},父进程ID:{os.getppid()}')

q=multiprocessing.Queue()
t=[]
lock=multiprocessing.Lock()
for i in range(10):
    t.append(multiprocessing.Process(target=demo,name=f'进程{i}'))

for i in t:
    i.start()

可以看到运行之后基本都是并发执行,这也是多进程效果更

(python38) [root@mysql01 dtask]# python 2.py 
执行时间: 2024-10-25 15:44:45.548511 子进程名字:进程5,当前进程ID:7678,父进程ID:7672
执行时间: 2024-10-25 15:44:45.549113 子进程名字:进程6,当前进程ID:7679,父进程ID:7672
执行时间: 2024-10-25 15:44:45.549570 子进程名字:进程1,当前进程ID:7674,父进程ID:7672
执行时间: 2024-10-25 15:44:45.549994 子进程名字:进程2,当前进程ID:7675,父进程ID:7672
执行时间: 2024-10-25 15:44:45.550426 子进程名字:进程3,当前进程ID:7676,父进程ID:7672
执行时间: 2024-10-25 15:44:45.550839 子进程名字:进程7,当前进程ID:7680,父进程ID:7672
执行时间: 2024-10-25 15:44:45.551425 子进程名字:进程8,当前进程ID:7681,父进程ID:7672
执行时间: 2024-10-25 15:44:45.551954 子进程名字:进程9,当前进程ID:7682,父进程ID:7672
执行时间: 2024-10-25 15:44:45.552496 子进程名字:进程4,当前进程ID:7677,父进程ID:7672
执行时间: 2024-10-25 15:44:45.553263 子进程名字:进程0,当前进程ID:7673,父进程ID:7672
(python38) [root@mysql01 dtask]# python 2.py 
执行时间: 2024-10-25 15:44:49.854005 子进程名字:进程5,当前进程ID:7692,父进程ID:7686
执行时间: 2024-10-25 15:44:49.854485 子进程名字:进程6,当前进程ID:7693,父进程ID:7686
执行时间: 2024-10-25 15:44:49.854808 子进程名字:进程1,当前进程ID:7688,父进程ID:7686
执行时间: 2024-10-25 15:44:49.855316 子进程名字:进程2,当前进程ID:7689,父进程ID:7686
执行时间: 2024-10-25 15:44:49.855698 子进程名字:进程3,当前进程ID:7690,父进程ID:7686
执行时间: 2024-10-25 15:44:49.856247 子进程名字:进程7,当前进程ID:7694,父进程ID:7686
执行时间: 2024-10-25 15:44:49.856574 子进程名字:进程8,当前进程ID:7695,父进程ID:7686
执行时间: 2024-10-25 15:44:49.857254 子进程名字:进程9,当前进程ID:7696,父进程ID:7686
执行时间: 2024-10-25 15:44:49.857582 子进程名字:进程4,当前进程ID:7691,父进程ID:7686
执行时间: 2024-10-25 15:44:49.858258 子进程名字:进程0,当前进程ID:7687,父进程ID:7686

下面采用lock

import multiprocessing,time,datetime,os

def demo():
    lock.acquire()
    time.sleep(1)
    print('执行时间:',datetime.datetime.now(),f'子进程名字:{multiprocessing.current_process().name},当前进程ID:{os.getpid()},父进程ID:{os.getppid()}')
    lock.release()

q=multiprocessing.Queue()
t=[]
lock=multiprocessing.Lock()
for i in range(10):
    t.append(multiprocessing.Process(target=demo,name=f'进程{i}'))

for i in t:
    i.start()

运行结果:

python38) [root@mysql01 dtask]# python 2.py 
执行时间: 2024-10-25 15:46:15.888807 子进程名字:进程5,当前进程ID:7789,父进程ID:7783
执行时间: 2024-10-25 15:46:16.889815 子进程名字:进程6,当前进程ID:7790,父进程ID:7783
执行时间: 2024-10-25 15:46:17.891551 子进程名字:进程1,当前进程ID:7785,父进程ID:7783
执行时间: 2024-10-25 15:46:18.893307 子进程名字:进程2,当前进程ID:7786,父进程ID:7783
执行时间: 2024-10-25 15:46:19.895166 子进程名字:进程3,当前进程ID:7787,父进程ID:7783
执行时间: 2024-10-25 15:46:20.896928 子进程名字:进程7,当前进程ID:7791,父进程ID:7783
执行时间: 2024-10-25 15:46:21.898912 子进程名字:进程8,当前进程ID:7792,父进程ID:7783
执行时间: 2024-10-25 15:46:22.900966 子进程名字:进程9,当前进程ID:7793,父进程ID:7783
执行时间: 2024-10-25 15:46:23.902843 子进程名字:进程4,当前进程ID:7788,父进程ID:7783
执行时间: 2024-10-25 15:46:24.904852 子进程名字:进程0,当前进程ID:7784,父进程ID:7783

可以看到时间都是相差一秒顺序执行所以没问题
看一个不同函数名获取lock的

import multiprocessing,time,datetime,os

def demo():
    lock.acquire()
    time.sleep(1)
    q.put(1)
    print('执行时间:',datetime.datetime.now(),f'子进程名字:{multiprocessing.current_process().name},当前进程ID:{os.getpid()},父进程ID:{os.getppid()}')
    lock.release()

def demo2():
    lock.acquire()
    time.sleep(1)
    q.put(2)
    print('执行时间:',datetime.datetime.now(),f'子进程名字:{multiprocessing.current_process().name},当前进程ID:{os.getpid()},父进程ID:{os.getppid()}')
    lock.release()

q=multiprocessing.Queue()
t=[]
lock=multiprocessing.Lock()
t.append(multiprocessing.Process(target=demo,name=f'进程1'))
t.append(multiprocessing.Process(target=demo2,name=f'进程2'))

for i in t:
    i.start()
for i in t:
    i.join()
while not q.empty():
    print('q的值:',q.get())

运行结果:

(python38) [root@mysql01 dtask]# python 2.py 
执行时间: 2024-10-25 15:55:21.224533 子进程名字:进程2,当前进程ID:8403,父进程ID:8401
执行时间: 2024-10-25 15:55:22.226918 子进程名字:进程1,当前进程ID:8402,父进程ID:8401
q的值: 2
q的值: 1

修改下代码:

import multiprocessing,time,datetime,os

def demo():
    lock.acquire()
    time.sleep(1)
    q.put(1)
    print('执行时间:',datetime.datetime.now(),f'子进程名字:{multiprocessing.current_process().name},当前进程ID:{os.getpid()},父进程ID:{os.getppid()}')
    lock.release()

def demo2():
    # lock.acquire()
    time.sleep(1)
    q.put(2)
    print('执行时间:',datetime.datetime.now(),f'子进程名字:{multiprocessing.current_process().name},当前进程ID:{os.getpid()},父进程ID:{os.getppid()}')
    # lock.release()

q=multiprocessing.Queue()
t=[]
lock=multiprocessing.Lock()
t.append(multiprocessing.Process(target=demo,name=f'进程1'))
t.append(multiprocessing.Process(target=demo2,name=f'进程2'))

for i in t:
    i.start()
for i in t:
    i.join()
while not q.empty():
    print('q的值:',q.get())

结果:

(python38) [root@mysql01 dtask]# python 2.py 
执行时间: 2024-10-25 15:57:27.649754 子进程名字:进程1,当前进程ID:8534,父进程ID:8533
执行时间: 2024-10-25 15:57:27.651128 子进程名字:进程2,当前进程ID:8535,父进程ID:8533
q的值: 1
q的值: 2

可以看到lock锁对在同一个父进程ID,会起到锁的作用
接下来我们建一个1.py脚本
脚本内容

import multiprocessing,time,datetime,os

def demo():
    lock.acquire()
    time.sleep(10)
    q.put(1)
    print('执行时间:',datetime.datetime.now(),f'子进程名字:{multiprocessing.current_process().name},当前进程ID:{os.getpid()},父进程ID:{os.getppid()}')
    lock.release()

def demo2():
    lock.acquire()
    time.sleep(10)
    q.put(2)
    print('执行时间:',datetime.datetime.now(),f'子进程名字:{multiprocessing.current_process().name},当前进程ID:{os.getpid()},父进程ID:{os.getppid()}')
    lock.release()

q=multiprocessing.Queue()
t=[]
lock=multiprocessing.Lock()
t.append(multiprocessing.Process(target=demo,name=f'进程1'))
t.append(multiprocessing.Process(target=demo2,name=f'进程2'))

print('1.py脚本主程序开始执行时间',datetime.datetime.now())
for i in t:
    i.start()
for i in t:
    i.join()
while not q.empty():
    print('q的值:',q.get())

2.py文件内容

import multiprocessing,time,datetime,os

def demo():
    lock.acquire()
    time.sleep(1)
    q.put(1)
    print('执行时间:',datetime.datetime.now(),f'子进程名字:{multiprocessing.current_process().name},当前进程ID:{os.getpid()},父进程ID:{os.getppid()}')
    lock.release()

def demo2():
    # lock.acquire()
    time.sleep(1)
    q.put(2)
    print('执行时间:',datetime.datetime.now(),f'子进程名字:{multiprocessing.current_process().name},当前进程ID:{os.getpid()},父进程ID:{os.getppid()}')
    # lock.release()

q=multiprocessing.Queue()
t=[]
lock=multiprocessing.Lock()
t.append(multiprocessing.Process(target=demo,name=f'进程1'))
t.append(multiprocessing.Process(target=demo2,name=f'进程2'))

print('2.py脚本主程序开始执行时间',datetime.datetime.now())
for i in t:
    i.start()
for i in t:
    i.join()
while not q.empty():
    print('q的值:',q.get())

同时执行1.py 和 2.py运行结果

(python38) [root@mysql01 dtask]# python 2.py 
2.py脚本主程序开始执行时间 2024-10-25 16:11:22.094498
执行时间: 2024-10-25 16:11:23.097780 子进程名字:进程1,当前进程ID:9620,父进程ID:9619
执行时间: 2024-10-25 16:11:23.098284 子进程名字:进程2,当前进程ID:9621,父进程ID:9619
q的值: 1
q的值: 2
(python38) [root@mysql01 dtask]# python 1.py 
1.py脚本主程序开始执行时间 2024-10-25 16:11:19.230205
执行时间: 2024-10-25 16:11:29.242953 子进程名字:进程1,当前进程ID:9615,父进程ID:9614
执行时间: 2024-10-25 16:11:39.254650 子进程名字:进程2,当前进程ID:9616,父进程ID:9614
q的值: 1
q的值: 2

还有文件输入情况,如果对文件进行lock,如果另外一个没加锁也是一样效果

import multiprocessing,time,datetime,os

def demo():
    lock.acquire()
    time.sleep(10)
    # for i in range(10):
    #     q.put(f'demo-{i}')
    with open('1.txt','a+',encoding='utf-8') as f:
        for i in range(10):
            print('开始写入demo数据')
            f.write(f'demo-{i}\n')
            f.flush()
    print('执行时间1:',datetime.datetime.now(),f'子进程名字:{multiprocessing.current_process().name},当前进程ID:{os.getpid()},父进程ID:{os.getppid()}')
    lock.release()

def demo2():
    # lock.acquire()
    # for i in range(10,20):
    #     q.put(f'demo2-{i}')
    print(f'开始时间:{datetime.datetime.now()}')
    with open('1.txt','a+',encoding='utf-8') as f:
        for i in range(11,40):
            time.sleep(1)
            print('开始写入demo2数据')
            f.write(f'demo2-{i}\n')
            f.flush()
    print('执行时间2:',datetime.datetime.now(),f'子进程名字:{multiprocessing.current_process().name},当前进程ID:{os.getpid()},父进程ID:{os.getppid()}')
    # lock.release()

q=multiprocessing.Queue()
t=[]
lock=multiprocessing.Lock()
t.append(multiprocessing.Process(target=demo,name=f'进程1'))
t.append(multiprocessing.Process(target=demo2,name=f'进程2'))
print('1.py脚本主程序开始执行时间',datetime.datetime.now())
for i in t:
    i.start()
for i in t:
    i.join()
while not q.empty():
    print('q的值:',q.get())
print('程序结束时间:',datetime.datetime.now())

执行结果

(python38) [root@mysql01 dtask]# python 1.py 
1.py脚本主程序开始执行时间 2024-10-28 15:09:06.458782
开始时间:2024-10-28 15:09:06.460716
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo数据
开始写入demo数据
开始写入demo数据
开始写入demo数据
开始写入demo数据
开始写入demo数据
开始写入demo数据
开始写入demo数据
开始写入demo数据
开始写入demo数据
执行时间1: 2024-10-28 15:09:16.470825 子进程名字:进程1,当前进程ID:16878,父进程ID:16877
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
开始写入demo2数据
执行时间2: 2024-10-28 15:09:35.521156 子进程名字:进程2,当前进程ID:16879,父进程ID:16877
程序结束时间: 2024-10-28 15:09:35.521762

(python38) [root@mysql01 dtask]# more 1.txt 
demo2-11
demo2-12
demo2-13
demo2-14
demo2-15
demo2-16
demo2-17
demo2-18
demo2-19
demo-0
demo-1
demo-2
demo-3
demo-4
demo-5
demo-6
demo-7
demo-8
demo-9
demo2-20
demo2-21
demo2-22
demo2-23
demo2-24
demo2-25
demo2-26
demo2-27
demo2-28
demo2-29
demo2-30
demo2-31
demo2-32
demo2-33
demo2-34
demo2-35
demo2-36
demo2-37
demo2-38
demo2-39

http://www.kler.cn/a/373688.html

相关文章:

  • Android 复习Path.Op.DIFFERENCE
  • ROS(快速初步入门)
  • linux之网络子系统- TCP连接建立过程 三次握手四次挥手
  • pgsql数据量大之后可能遇到的问题
  • MFC工控项目实例二十七添加产品参数
  • windows下安装python库wordCloud报错
  • 奥数与C++小学四年级(第十二题 装礼盒)
  • 【unity框架开发14】状态机的封装与实现
  • 正则表达式和通配符
  • 【C/C++】模拟实现strlen
  • 一个简单的Http根据规则自动路由
  • 沈阳乐晟睿浩科技有限公司抖音小店实力电商新星
  • c语言水仙花,超简单讲解
  • Java方法重写
  • C语言的知识框架
  • CSS秘籍-高效样式技巧
  • 【成都新篇】龙信科技电子取证实验室,引领科技取证新时代
  • PIDNet(语义分割)排坑
  • HarmonyOS生命周期
  • 基于局部近似的模型解释方法
  • 【数据结构】ArrayList的模拟实现--Java
  • android12属性设置
  • 使用 NCC 和 PKG 打包 Node.js 项目为可执行文件(Linux ,macOS,Windows)
  • 设计一个灵活的RPC架构
  • AI代币是什么?AI与Web3结合的未来方向在哪里?
  • Transformer-BiGRU多特征输入时间序列预测(Pytorch)