在python3中发送到程序的标准输入 [英] Sending to the stdin of a program in python3

查看:51
本文介绍了在python3中发送到程序的标准输入的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我必须存档,ma​​in.pychild.py.

我正在尝试向 ma​​in.py 的标准输入发送一个字符串.

I am trying to send a string to the stdin of main.py.

这是我不完整的代码:

from subprocess import *
import time

def main():
    program = Popen(['python.exe'. 'child.py', 'start'])
    while True: #waiting for'1' to be sent to the stdin
        if sys.stdin == '1':
            print('text)

if __name__ == '__main__':
    main()

child.py

import sys

if sys.argv[1] == 'start':
    inp = input('Do you want to send the argument?\n').lower()
    if inp == 'no':
        sys.exit()
    elif inp == 'yes':
        #Somehow send '1' to the stdin of 1.py while it is running

我不知道该怎么做.

我正在使用 python 3.5.1 运行 Windows 10

I am running windows 10 with python 3.5.1

-谢谢

当我将参数发送回 main.py 时,我无法重新打开程序.os.system 重新打开了对我来说没有用的程序.

When I am sending the argument back to main.py, I can not re-open the program. os.system re-opens the program which is not useful in my case.

这些程序是我正在尝试做的事情的一个小演示.在我的实际程序中,我无法做到这一点,因为这两个程序相互通信",需要始终打开.

These programs are a small demo of what I am trying to do. In my actual program, I am not able to do that as the two programs are "communicating" with each other an need to be open at all times.

我需要回答的是一种可能使用 stdin 向 main.py 发送参数的方法,但是当我发送参数时,它无法重新打开程序.像 os.system 这样的一些例子重新打开程序,这不是我想要做的.我需要一直打开 main.py.

What I need answered is a way to send an argument to main.py perhaps using stdin but when I am sending my argument, It can not re-open the program. Some examples like os.system re-open the program which is not what I am trying to do. I need main.py open at all times.

我的当前新代码不起作用.一个窗口弹出然后关闭.

I have my new current code which is not working. A window pops up and then closes.

from subprocess import Popen, PIPE, STDOUT
x = Popen(['python.exe', '2.py', 'start'], stdout=PIPE, stdin=PIPE, stderr=STDOUT)
while x.poll() is None:
    if b'Do you want to send the argument?' in x.stdout.read():
        x.stdin.write(b'yes\n')

child.py

import sys
import time
time.sleep(1)
if 1 = 1:
    inp = input('Do you want to send the argument?\n').lower()
    if inp == 'no':
        sys.exit()
    elif inp == 'yes':
        sys.stdout.write('1')
        sys.stdout.flush()

这是我的代码.

推荐答案

你需要的是(在 main.py 中):

What you need is something along the lines of (in main.py):

from subprocess import Popen, PIPE, STDOUT
x = Popen(['some_child.exe', 'parameter'], stdout=PIPE, stdin=PIPE, stderr=STDOUT)

while x.poll() is None:
    child_output = x.stdout.readline()
    print(child_output)
    if b'Do you want to send the argument?' in child_output:
        x.stdin.write(b'yes\n')
        x.stdin.flush()
x.stdout.close()
x.stdin.close()

您假设 child.exe(在您的模型演示中,python.exe)正在通过 main.py 通信>sys.stdin/stdout,但是这些 I/O 用于与产生进程的 shell 进行通信.

You're assuming child.exe (in your mockup demo, python.exe) is communicating with main.py via sys.stdin/stdout, however these I/O's are used to communicate with the shell that spawned the process.

很像孩子的 stdout/stdin 将与产生该进程的 shell 进行通信,在这种情况下是 Popen().

Much like the childs stdout/stdin will be communicating with the shell that spawned that process, in this case Popen().

subprocess.Popen(...) 的每个衍生子进程都将与它自己的 stdout/stdin/stderr 隔离,否则每个子进程都会弄得一团糟您的主进程标准输出/标准输入.这意味着您必须检查该特定子进程的输出,并按照上面的示例进行相应的写入.

Each spawned child process of subprocess.Popen(...) will be isolated with it's own stdout/stdin/stderr, otherwise every subprocess would make a huge mess of your main process stdout/stdin. This means you'll have to check for output on that particular subprocess and write to it accordingly as done in the above example.

一种看待它的方式是这样的:

One way to look at it is this:

您正在启动 main.py,并通过 sys.stdoutsys.stdin 与它通信.main.py 中的每个 input() 都会向 sys.stdout 输出一些内容,以便您阅读.

You're starting main.py, and you communicate with it via sys.stdout and sys.stdin. Each input() in main.py will output something to sys.stdout so you can read it.

完全相同的逻辑适用于 child.exe,其中每个 input() 都会输出一些东西到它的 sys.stdout (- 但请记住 - sys 不是跨进程的共享变量).

Exactly the same logic applies to child.exe where every input() will output something to it's sys.stdout (- But remember - sys is not a shared variable across processes).

import sys

if sys.argv[1] == 'start':
    inp = input('Do you want to send the argument?\n').lower()
    if inp == 'no':
        sys.exit()
    elif inp == 'yes':
        #Somehow send '1' to the stdin of 1.py while it is running
        sys.stdout.write('1')
        sys.stdout.flush()

但是一个简单的 print(1) 会做同样的事情,因为它实际上会为你输出 1sys.stdout.

But a simple print(1) would do the same because it will essentially output the 1 to sys.stdout for you.

Edit 2018:不要忘记关闭您的输入和输出,因为它们可能会在您的文件系统上留下打开的文件描述符,占用资源并在以后的生活中引起问题.

Edit 2018: Don't forget to close your inputs and outputs, as they might leave open file descriptors on your file system, hogging resources and causing problems later in life.

假设您可以控制 child.exe 的代码并且您可以以任何方式修改通信管道,那么其他一些选项是:

Assuming you have control of the code to child.exe and you can modify the communication pipe in any way, some other options are:

  • .readline() 会假设数据中有一个 \n ,很可能在最后.我切换到 .readline() 有两个原因,.read() 将挂起并等待 EOF 除非您指定确切的字节数阅读,如果我不骑自行车.为了能够读取各种输出,您需要合并 select.select() 进入您的代码 - 或某种缓冲区,您可以在其中调用 x.stdout.read(1) 一次读取一个字节.因为如果您尝试读取 .read(1024) 并且缓冲区中没有 1024 个字节,您的读取将挂起直到有 1024 个字符.

  • .readline() will assume there's a \n somewhere in your data, most likely at the end. I switched to .readline() for two reasons, .read() will hang and wait for EOF unless you specify exactly how many bytes to read, if I'm not out on a bicycle. To be able to read all kinds of output you need to incorporate select.select() into your code - or a buffer of some sort where you call x.stdout.read(1) to read one byte at a time. Because if you try to read .read(1024) and there's not 1024 bytes in the buffer, your read will hang until there are 1024 characters.

我故意在你的 child.py 代码中留下了一个错误(我的作品)——它是微不足道的基本 Python——希望它是关于如何调试错误的学习经验(你提到你不擅长,这是一种学习方式).

I left a bug in your child.py code on purpose (mine works) - It's trivial and basic Python - in hopes that it's a learning experience on how to debug errors (you mentioned you're not good at it, this is a way to learn).

这篇关于在python3中发送到程序的标准输入的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆