java system.in 是否可以在不使用线程的情况下同时与输入源代码一起工作

Can java system.in work together with input source code at same time without using thread

说我的要求是: 用户在控制台中输入内容(来自 system.in)或套接字接收内容,继续下一步。

所以我有一个扫描仪

Scanner sc = new Scanner(System.in);

有一个 Udp 客户端。 (不同的输入源)

DatagramSocket clientSocket = new DatagramSocket();

我的密码是

while (true) {
     if (sc.hasNext()) {
        String str = sc.next();
        proceed(str)
     } else { 
        clientSocket.receive(pack);
        proceed(pack)
     }
}

显然这段代码是行不通的。因为在检查 sc.hasNext() 时,java 正在等待用户在控制台中键入一些输入。目前我能做的是为 Udp 客户端打开一个线程。如果我改变顺序,

while (true) {
         clientSocket.receive(pack);
         if (not receive)  read from system.in
    }

这没有意义,因为 receive() 会一直等待直到收到东西,它永远不会同时从 system.in 读取。

那么如何在不使用线程的情况下实现我的要求?

受@Andriy Kryvtsun 回答的启发,我做了一个快速测试 正如他所说,这是在某种程度上使用非阻塞读取,并让套接字超时,以模拟

        InputStream ins = System.in;
    byte buffer[] = new byte[512];
    BufferedReader reader = new BufferedReader(new InputStreamReader(ins));
    DatagramSocket clientSocket = new DatagramSocket();
    System.out.println("From buffer:" + clientSocket.getLocalPort());

    while (true) {
        try {
            if (ins.available() > 0) {
                String line = reader.readLine();
                System.out.println("Read:" + line);
            } else {

                DatagramPacket pack = new DatagramPacket(buffer,buffer.length);
                clientSocket.setSoTimeout(2000);
                clientSocket.receive(pack);
                System.out.println("Receive: " + new String(pack.getData()));
            }
        } catch (IOException e1) {

        }
    }

在使用阻塞 Scanner#hasNext() 调用之前,使用解锁方法调用 InputStream#available() 获取信息是否已准备好阅读。

您也可以在调用阻塞 receive(DatagramPacket p) 方法之前调用 DatagramSocket#setSoTimeout(int timeout)。因此,您可以在 timeout 期间模拟无阻塞读取后打破 receive 方法内的无限等待。