当前位置: 首页 > 知识库问答 >
问题:

使用子进程PIPE在Python脚本之间发送字符串

赵志
2023-03-14

我想在我的主Python程序中使用subprocess打开一个Python脚本。我希望这两个程序都在运行时能够相互聊天,这样我就可以监视从脚本中的活动,也就是说,我需要它们在彼此之间发送字符串。

主程序将具有与此类似的功能,该功能将与从属脚本通信并监控从属脚本:

脚本1

import subprocess
import pickle
import sys
import time
import os

def communicate(clock_speed, channel_number, frequency):
    p = subprocess.Popen(['C:\\Python27\\pythonw','test.py'], stdin=subprocess.PIPE, stdout=subprocess.PIPE)
    data = pickle.dumps([clock_speed, channel_number, frequency]).replace("\n", "\\()")
    print data
    p.stdin.write("Start\n")
    print p.stdout.read()
    p.stdin.write(data + "\n")
    p.poll()
    print p.stdout.readline()
    print "return:" + p.stdout.readline()
    #p.kill()

if __name__ == '__main__':
    print "GO"
    communicate(clock_speed = 400, channel_number = 0, frequency = 5*1e6)

测试。py脚本与此类似:

脚本2

import ctypes
import pickle
import time
import sys

start = raw_input("")
sys.stdout.write("Ready For Data")
data = raw_input("")
data = pickle.loads(data.replace("\\()", "\n"))
sys.stdout.write(str(data))
###BUNCH OF OTHER STUFF###

我希望这些脚本执行以下操作:

  1. 脚本1使用Popen打开脚本2
  2. 脚本1发送字符串开始\n
  3. 脚本2读取这个字符串,并发送字符串准备数据
  4. 脚本1读取这个字符串,并将提取的数据发送到脚本2
  5. 然后无论...

主要问题是如何做第2-4部分。然后两个脚本之间的其余通信应该遵循。到目前为止,我只能在脚本2终止后读取它的字符串。

任何帮助都非常感谢。

更新:

脚本1必须使用32位Python运行,而脚本2必须使用64位Python运行。

共有2个答案

常炯
2023-03-14

我也遇到了类似的问题,在不同进程之间发送一般Python对象时,如果不知道另一方何时没有发送对象或对象何时关闭,就无法实现。还尝试使用多处理。队列通常意味着流程需要由当前流程启动,而这在两个流程想要协作时并不总是如此。

为了解决这个问题,我使用了picklepipe模块,它定义了一个通用的对象序列化管道接口,以及一个使用pickle协议(称为picklepipe)的管道(也是一个使用MarshalPipe协议的管道)。它可以发送的不仅仅是字符串,它还可以将任何可pickle对象发送给它的对等对象。

管道甚至可以选择,这意味着当准备接收新对象时,选择器模块(或选择器2选择器34)可以将管道用作文件对象。这使得等待许多不同管道准备就绪非常有效。

支持Python 2.7(可能还有2.6)和所有主要平台。甚至可以在两个不同版本的Python之间发送对象!查看项目文档或在Github上查看源代码。

披露:我是泡菜管的作者。我很乐意听到你的反馈。:)

柯浩壤
2023-03-14

管道的问题是,如果您调用读取操作而没有任何内容可读取,那么您的代码将被暂停,直到另一方为您写入要读取的内容为止。此外,如果您写得太多,您的下一个写操作可能会阻塞,直到另一方从管道中读取某些内容并释放它。

您可以进行“非阻塞调用”,在这些情况下会返回错误,而不是阻塞,但您的html" target="_blank">应用程序仍需要明智地处理错误。

在任何情况下,您都需要设置某种协议。想想HTTP,或者你熟悉的任何其他协议:有请求和响应,当你阅读这两个协议中的任何一个时,协议总是告诉你是否还有其他需要阅读的内容。这样,您就可以随时做出是否等待更多数据的明智决定。

这里有一个有效的例子。它的工作原理是因为有以下协议:

  • p1发送一行,以“\n”结尾
  • p2也是如此
  • p1发送另一条线路
  • p2也是如此
  • 两人都很开心,都退出了

为了给管道写一行(在任何一边)并确保它到达管道上,我调用写(),然后调用flush()

为了从管道(任一侧)读取一行数据,但不超过一个字节,从而阻塞代码,直到该行准备就绪,并且不再超过该行,我使用readline()

您还可以进行其他呼叫和其他协议,包括现成的协议,但是单行协议对于简单的事情和像这样的演示非常有效。

p1。py:

import subprocess

p = subprocess.Popen(['python', 'p2.py'], stdin=subprocess.PIPE, stdout=subprocess.PIPE)
p.stdin.write("Hello\n")
p.stdin.flush()
print 'got', p.stdout.readline().strip()
p.stdin.write("How are you?\n")
p.stdin.flush()
print 'got', p.stdout.readline().strip()

p2.py:

import sys

data = sys.stdin.readline()
sys.stdout.write("Hm.\n")
sys.stdout.flush()
data = sys.stdin.readline()
sys.stdout.write("Whatever.\n")
sys.stdout.flush()
 类似资料:
  • 我有两个php脚本:main.php和script.php。 我正在将变量从main.php发送到script.php。在script.php文件中,我使用这个变量从MySQL数据库中获取某些数据。这个数据存储在变量中,需要发送回main.php文件。 为了在两个文件之间传输变量,我使用,但在打开main.php文件时,我得到一个。 在脚本之间传输这两个变量的正确方法是什么? main.php s

  • 问题内容: 有没有一种方法可以使用Python脚本中的POST发送文件? 问题答案: 通过请求,上传Multipart编码的文件非常简单: 而已。我不是在开玩笑-这是一行代码。文件已发送。让我们检查:

  • 问题内容: 我有一个脚本,执行时会向用户询问某些查询,并以json格式构建输出框架。使用python子进程,我可以从另一个名为的脚本中调用此脚本。一切都按预期工作,除了我无法在变量中获取输出?我正在Python 3中执行此操作。 问题答案: 要使用模块从另一个脚本中调用Python脚本并传递一些输入并获取其输出,请执行以下操作: 这里定义了功能。 更为灵活的替代方法是导入模块a并调用函数以获取结果

  • 我制作了一个简单的服务器程序,可以同时从4个不同的客户端接收数据。现在我想用AES-128加密发送一些数据,但应该在服务器端解码。以下是我的服务器代码: 我从客户端发送这样的数据 我应该如何修改我的客户端代码和服务器代码,以便在其中包含AES-128加密。。请在这方面帮助我。

  • 问题内容: 我在使用Python 3中的smtplib向unicode字符发送电子邮件时遇到问题,这在3.1.1中失败,但在2.5.4中有效: 我尝试了文档中的示例,但也失败了。 http://docs.python.org/3.1/library/email- examples.html ,以MIME消息示例的形式发送目录的内容 有什么建议? 问题答案: 关键在docs中: MIMEText类是

  • 问题内容: 如何找到两个子字符串之间的字符串? 我当前的方法是这样的: 但是,这似乎效率很低而且不合Python。什么是做这样的更好的方法? 忘了提:该字符串可能无法启动,并最终和。他们之前和之后的字符可能更多。 问题答案: