日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > python >内容正文

python

python管道通信_Python进程通信之匿名管道实例讲解

發布時間:2023/12/1 python 24 豆豆
生活随笔 收集整理的這篇文章主要介紹了 python管道通信_Python进程通信之匿名管道实例讲解 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

匿名管道

管道是一個單向通道,有點類似共享內存緩存.管道有兩端,包括輸入端和輸出端.對于一個進程的而言,它只能看到管道一端,即要么是輸入端要么是輸出端.

os.pipe()返回2個文件描述符(r, w),表示可讀的和可寫的.示例代碼如下:

復制代碼 代碼如下:

#!/usr/bin/python

import time

import os

def child(wpipe):

print('hello from child', os.getpid())

while True:

msg = 'how are you\n'.encode()

os.write(wpipe, msg)

time.sleep(1)

def parent():

rpipe, wpipe = os.pipe()

pid = os.fork()

if pid == 0:

child(wpipe)

assert False, 'fork child process error!'

else:

os.close(wpipe)

print('hello from parent', os.getpid(), pid)

fobj = os.fdopen(rpipe, 'r')

while True:

recv = os.read(rpipe, 32)

print recv

parent()

輸出如下:

復制代碼 代碼如下:

('hello from parent', 5053, 5054)

('hello from child', 5054)

how are you

how are you

how are you

how are you

我們也可以改進代碼,不用os.read()從管道中讀取二進制字節,而是從文件對象中讀取字符串.這時需要用到os.fdopen()把底層的文件描述符(管道)包裝成文件對象,然后再用文件對象中的readline()方法讀取.這里請注意文件對象的readline()方法總是讀取有換行符'\n'的一行,而且連換行符也讀取出來.還有一點要改進的地方是,把父進程和子進程的管道中不用的一端關閉掉.

復制代碼 代碼如下:

#!/usr/bin/python

import time

import os

def child(wpipe):

print('hello from child', os.getpid())

while True:

msg = 'how are you\n'.encode()

os.write(wpipe, msg)

time.sleep(1)

def parent():

rpipe, wpipe = os.pipe()

pid = os.fork()

if pid == 0:

os.close(rpipe)

child(wpipe)

assert False, 'fork child process error!'

else:

os.close(wpipe)

print('hello from parent', os.getpid(), pid)

fobj = os.fdopen(rpipe, 'r')

while True:

recv = fobj.readline()[:-1]

print recv

parent()

輸出如下:

復制代碼 代碼如下:

('hello from parent', 5108, 5109)

('hello from child', 5109)

how are you

how are you

how are you

如果要與子進程進行雙向通信,只有一個pipe管道是不夠的,需要2個pipe管道才行.以下示例在父進程新建了2個管道,然后再fork子進程.os.dup2()實現輸出和輸入的重定向.spawn功能類似于subprocess.Popen(),既能發送消息給子進程,由能從子子進程獲取返回數據.

復制代碼 代碼如下:

#!/usr/bin/python

#coding=utf-8

import os, sys

def spawn(prog, *args):

stdinFd = sys.stdin.fileno()

stdoutFd = sys.stdout.fileno()

parentStdin, childStdout = os.pipe()

childStdin, parentStdout= os.pipe()

pid = os.fork()

if pid:

os.close(childStdin)

os.close(childStdout)

os.dup2(parentStdin, stdinFd)#輸入流綁定到管道,將輸入重定向到管道一端parentStdin

os.dup2(parentStdout, stdoutFd)#輸出流綁定到管道,發送到子進程childStdin

else:

os.close(parentStdin)

os.close(parentStdout)

os.dup2(childStdin, stdinFd)#輸入流綁定到管道

os.dup2(childStdout, stdoutFd)

args = (prog, ) + args

os.execvp(prog, args)

assert False, 'execvp failed!'

if __name__ == '__main__':

mypid = os.getpid()

spawn('python', 'pipetest.py', 'spam')

print 'Hello 1 from parent', mypid #打印到輸出流parentStdout, 經管道發送到子進程childStdin

sys.stdout.flush()

reply = raw_input()

sys.stderr.write('Parent got: "%s"\n' % reply)#stderr沒有綁定到管道上

print 'Hello 2 from parent', mypid

sys.stdout.flush()

reply = sys.stdin.readline()#另外一種方式獲得子進程返回信息

sys.stderr.write('Parent got: "%s"\n' % reply[:-1])

pipetest.py代碼如下:

復制代碼 代碼如下:

#coding=utf-8

import os, time, sys

mypid = os.getpid()

parentpid = os.getppid()

sys.stderr.write('child %d of %d got arg: "%s"\n' %(mypid, parentpid, sys.argv[1]))

for i in range(2):

time.sleep(3)

recv = raw_input()#從管道獲取數據,來源于父經常stdout

time.sleep(3)

send = 'Child %d got: [%s]' % (mypid, recv)

print(send)#stdout綁定到管道上,發送到父進程stdin

sys.stdout.flush()

輸出:

復制代碼 代碼如下:

child 7265 of 7264 got arg: "spam"

Parent got: "Child 7265 got: [Hello 1 from parent 7264]"

Parent got: "Child 7265 got: [Hello 2 from parent 7264]"

總結

以上是生活随笔為你收集整理的python管道通信_Python进程通信之匿名管道实例讲解的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。