【问题标题】:How to make System.out calls without affecting current users input (System.in) in console application?如何在不影响控制台应用程序中当前用户输入(System.in)的情况下进行 System.out 调用?
【发布时间】:2017-11-08 12:28:45
【问题描述】:

我有一个 Java 控制台应用程序,我经常在其中读取用户输入的命令。一些命令必须在不同的线程中运行,并且只是定期打印到它们运行的​​输出结果,每 10 秒一次。如何在不影响用户的情况下做到这一点。

例子:

ru你好!n

这意味着当用户键入“运行”命令时,一个线程向控制台输出了一个输出。 有没有标准的方法可以省略这个?

【问题讨论】:

  • 考虑将那些其他线程的输出写入某个日志文件而不是 System.out
  • 当然。创建一个单独的用户界面
  • 您希望看到什么?
  • @fishinear 我想在当前输入行上方查看线程的输出。 E.e.: {code}你好! >run{code} 或者至少:{code}>ru 你好! >运行{代码}
  • @Stultuske,不可能 - 控制台应用程序,可以在远程终端中执行。

标签: java console-application


【解决方案1】:

您可以使用Semaphore 来处理多个线程之间的共享资源。

我基于这个link写了一个简单的例子。下面是从控制台获取输入的主类。

package multithread;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Semaphore;
import java.util.concurrent.TimeUnit;

public class MainThread {

    public static void main(String[] args) throws IOException, InterruptedException {
        System.out.println("Starting...");
        Semaphore semaphore = new Semaphore(1);
        ExecutorService execService = Executors.newFixedThreadPool(8);
        for (int i = 0; i < 100; i++) {
            execService.submit(new BackgroundTask(semaphore, i));
        }
        BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
        String line;
        for (int i = 0; i < 10; i++) {
            semaphore.acquire();
            System.out.print("$ ");
            line = reader.readLine();
            System.out.println(line);
            semaphore.release();
            Thread.sleep(1000);
        }
        reader.close();
        execService.awaitTermination(10, TimeUnit.MINUTES);
    }
}

这是打印到控制台的后台任务类。

package multithread;

import java.util.concurrent.Semaphore;

public class BackgroundTask implements Runnable {

    private Semaphore semaphore;

    private int id;

    public BackgroundTask(Semaphore semaphore, int id) {
        this.semaphore = semaphore;
        this.id = id;
    }

    @Override
    public void run() {
        for (int i = 0; i < 10; i++) {
            try {
                Thread.sleep(1000);
                semaphore.acquire();
                System.out.println("Hello from " + id);
                semaphore.release();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }

}

【讨论】:

  • 这似乎可行,将检查并返回结果。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-10-24
  • 1970-01-01
  • 2021-07-31
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多