简体   繁体   English

接受用户输入时 Java 扫描仪出现奇怪错误

[英]Strange error with Java Scanner when taking user input

I am working on a Java project that includes a simple menu system.我正在开发一个包含简单菜单系统的 Java 项目。 I am getting some strange errors when the code reaches folling line in the Menu() function:当代码到达 Menu() function 中的以下行时,我遇到了一些奇怪的错误:

int menuInput = Integer.parseInt(scanner.nextLine()); 

I have seen similar issues that people have posted, but nothing I do seems to fix the issue.我看到了人们发布的类似问题,但我似乎没有解决这个问题。 I have posted the full class below.我在下面发布了完整的 class。

package Compiler;

import org.antlr.v4.runtime.*;
import org.antlr.v4.runtime.tree.*;
import java.io.IOException;
import java.util.Scanner;

public class Main {
    public static void main(String[] args) throws IOException {
        System.out.println("Copy and paste code to be compiled here, then press ENTER followed by CTRL+D:\n");

        CharStream input = CharStreams.fromStream(System.in);
        GrammarLexer lexer = new GrammarLexer(input);
        CommonTokenStream tokens = new CommonTokenStream(lexer);
        GrammarParser parser = new GrammarParser(tokens);
        ParseTree tree = parser.program();
        Worker worker = new Worker(parser.getRuleNames());
        worker.visit(tree);
        Menu(worker);
    }

    private static void Menu(Worker worker) {
        while (true) {
            System.out.println("1-4?");

            Scanner scanner = new Scanner(System.in);
            int menuInput = Integer.parseInt(scanner.nextLine());   // THIS IS WHERE THE CODE CRASHES

            try {
                switch(menuInput) {
                    case 1: {
                        worker.PrintParseTree();
                        break;
                    } case 2: {
                        String searchQuery = scanner.nextLine();
                        worker.SearchParseTree(searchQuery);
                        break;
                    } case 3: {
                        worker.PrintJSCode();
                        break;
                    } case 4: {
                        worker.PrintWACode();
                        break;
                    } default: {
                        System.out.println("ERROR: Invalid input, please try again...");
                        break;
                    }
                }
            } catch (Exception e) {
                System.out.println(e);
            }
        }
    }
}

This is the error that continues to occur.这是继续发生的错误。 The code crashes before giving the user opportunity to make any input:代码在让用户有机会进行任何输入之前崩溃:

Exception in thread "main" java.util.NoSuchElementException: No line found
    at java.base/java.util.Scanner.nextLine(Scanner.java:1651)
    at Compiler.Main.Menu(Main.java:44)
    at Compiler.Main.main(Main.java:29)

Update: From looks of things from ANTLR website, the fromStream method will open the System.in stream, then closes it (see quote from website).更新:从 ANTLR 网站的情况来看,fromStream 方法将打开 System.in stream,然后将其关闭(参见网站的引用)。

Creates a CharStream given an opened InputStream containing UTF-8 bytes.给定一个包含 UTF-8 字节的已打开 InputStream,创建一个 CharStream。 Reads the entire contents of the InputStream into the result before returning, then closes the InputStream.在返回之前将 InputStream 的全部内容读入结果中,然后关闭 InputStream。

Can anybody provide a workaround for this?任何人都可以为此提供解决方法吗?

I think somewhere inside of the worker methods you close the CharStream input, which closes System.in, which means there are no more lines for the scanner to read.我认为在工作方法内部的某个地方关闭了 CharStream 输入,它关闭了 System.in,这意味着扫描仪没有更多的行可以读取。

Edit:编辑:

I don't have access to the CharStream class, so I substited it for InputStreamReader in my example.我无权访问 CharStream class,因此在示例中将其替换为 InputStreamReader。 The following code gives the same error that yours does.以下代码给出了与您的相同的错误。

//When the program starts, System.in is open.

InputStreamReader is = new InputStreamReader(System.in);
is.close(); 
// When we close the InputStreamReader, the underlying System.in is also closed.

Scanner scanner = new Scanner(System.in); 
//It successfully creates a scanner for System.in, even if it's closed.

scanner.nextLine();
//But it can't read, since the underlying stream is now closed.

I'm not concerned about instances of System.in.close() , but rather input.close() which also affects System.in .我不关心System.in.close()的实例,而是input.close()这也会影响System.in input may of course have a different name in different classes. input在不同的类中当然可能有不同的名称。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM