首页 > 解决方案 > How can I properly run 2 threads that await things at the same time?

问题描述

Basically, I have 2 threads, receive and send. I want to be able to type a message, and whenever I get a new message it just gets 'printed above the line I am typing in'. first what I thought would work, and you can just paste this it will run:

import multiprocessing
import time
from reprint import output
import time
import random
import sys

def receiveThread(queue):
    i = 0
    while True:
        queue.put(i)
        i+=1
        time.sleep(0.5)

def sendThread(queue):
    while True:
        a = sys.stdin.read(1)
        if (a != ""):
            queue.put(a)
        


if __name__ == "__main__":
    send_queue = multiprocessing.Queue()
    receive_queue = multiprocessing.Queue()

    send_thread = multiprocessing.Process(target=sendThread, args=[send_queue],)
    receive_thread = multiprocessing.Process(target=receiveThread, args=[receive_queue],)
    receive_thread.start()
    send_thread.start()

    with output(initial_len=2, interval=0) as output_lines:
        while True:
            output_lines[0] = "Received:  {}".format(str(receive_queue.get()))
            output_lines[1] = "Last Sent: {}".format(str(send_queue.get()))

But what happens here is that i cannot send data. The input doesn't give me an EOF unlike when I put a = input(), but it overwrites whatever I put in that line, so how can I wait for the input in one thread while the other one works?

EXPECTED BEHAVOIR:

first line goes Received: 0, 1, 2, 3, 4...

second line goes [my input until I press enter, then my input]

ACTUAL BEHAVIOR if i don't check if input != ""

first line as expected only that the input overwrites the first couple of letters until it resets to Received

second line is always empty, maybe bc stdin only is filled for that one time i press enter and then always returns empty?

ACTUAL BEHAVIOR if i check if input != ""

first line stays: received = 0

second line is just like whatever i enter, if i press enter it goes into a new line where i then enter stuff

标签: pythoninputcommand-line-interfacepython-multiprocessing

解决方案


不要使用同一个套接字与...自身通信。这可能是可能的,我不确定,但这肯定是不正常的。而是制作一个套接字对,一个用于发送线程,一个用于接收线程,例如这对我有用:

import socket;
import multiprocessing;

def receiveThread(sock):
    while True:
        msg = sock.recv(1024)
        print(msg.decode("utf-8"))

def sendThread(sock):
    while True:
        # msg=input("client: ")
        # input() is broken on my system :(
        msg="foo"
        sock.send(bytes(msg,"utf8"))

pair = socket.socketpair()
recieve_thread_socket = pair[0]
send_thread_socket = pair[1]

send_thread = multiprocessing.Process(target=sendThread, args=[recieve_thread_socket])
receive_thread = multiprocessing.Process(target=receiveThread,args=[send_thread_socket])
send_thread.start()
receive_thread.start()

推荐阅读