在 Java 中处理初始值后不要关闭标准输入
Don't close stdin after initial value was processed in Java
我正在制作简单的控制台应用程序。我的主循环看起来像这样。
var s = new Scanner(System.in);
while (appShouldRun) {
var action = s.nextLine();
// proccess action
}
当我 运行 标准输入为空的应用程序时它工作正常。
java -jar app.jar
但我想在文件中准备一些场景。 运行 他们然后等待下一个用户输入。
预期行为:
java -jar app.jar < scenario.txt
output of commands from file
| <- cursor, waiting for user input
// scenario.txt
cmd1
cmd2
cmd3
.
.
.
问题是,当我 运行 使用 od std 进行编程时,它可以正确处理命令,但随后会抛出
java.util.NoSuchElementException: No line found
我认为这是因为在处理文件中的所有行后标准输入被关闭。
我错了吗?
如何修复代码以获得预期的行为?
谢谢
当您使用 <
重定向标准输入时,它连接到输入文件,根本没有连接 到控制台。
如果您希望您的程序在控制台上接收输入,那么您不能重定向标准输入。您应该将文件名作为命令行参数。打开它,读取它,关闭它,然后处理标准输入。
或者,如果你真的想要,并且你在 unix/linux/macOS 系统上,你可以 运行 像这样,使用 cat
命令将标准输入连接到其他:
cat scenario.txt - | java -jar app.jar
我尝试过尽可能少地更改代码。这会像你想要的那样读取整个文件并且没有异常结束
public class Main {
public static void main(String[] args) {
Scanner s = new Scanner(System.in);
boolean appShouldRun = true;
while (appShouldRun) {
String action = s.nextLine();
System.out.println("got: " + action);
appShouldRun = s.hasNext();
}
}
}
我正在制作简单的控制台应用程序。我的主循环看起来像这样。
var s = new Scanner(System.in);
while (appShouldRun) {
var action = s.nextLine();
// proccess action
}
当我 运行 标准输入为空的应用程序时它工作正常。
java -jar app.jar
但我想在文件中准备一些场景。 运行 他们然后等待下一个用户输入。
预期行为:
java -jar app.jar < scenario.txt
output of commands from file
| <- cursor, waiting for user input
// scenario.txt
cmd1
cmd2
cmd3
.
.
.
问题是,当我 运行 使用 od std 进行编程时,它可以正确处理命令,但随后会抛出
java.util.NoSuchElementException: No line found
我认为这是因为在处理文件中的所有行后标准输入被关闭。 我错了吗? 如何修复代码以获得预期的行为?
谢谢
当您使用 <
重定向标准输入时,它连接到输入文件,根本没有连接 到控制台。
如果您希望您的程序在控制台上接收输入,那么您不能重定向标准输入。您应该将文件名作为命令行参数。打开它,读取它,关闭它,然后处理标准输入。
或者,如果你真的想要,并且你在 unix/linux/macOS 系统上,你可以 运行 像这样,使用 cat
命令将标准输入连接到其他:
cat scenario.txt - | java -jar app.jar
我尝试过尽可能少地更改代码。这会像你想要的那样读取整个文件并且没有异常结束
public class Main {
public static void main(String[] args) {
Scanner s = new Scanner(System.in);
boolean appShouldRun = true;
while (appShouldRun) {
String action = s.nextLine();
System.out.println("got: " + action);
appShouldRun = s.hasNext();
}
}
}