问题描述
我之前使用了几种方法来接受用户输入,并将其作为特定数据类型返回给调用它的方法。我在之前的项目中使用过这些方法或它们的变体。
I have several methods that I've used previously to accept user input and return it as a certain data type to the method that calls for it. I have used these methods, or variations of them, in previous projects.
我采用了我用于字符串的方法来选择给定的第一个字符并返回,以便我可以在菜单中使用它。每次启动应用程序时,都会出现主菜单并等待用户输入。收到此输入后,程序会一直循环直到停止。这是我捕获char的方法:
I've adopted the method that I used for string to select the first char given and return that, so that I can use this in a menu. Every time I start the application, the main menu appears and waits for user input. After receiving this input, the program loops continuously until stopped. Here is my method for capturing the char:
private char getUserChar(String prompt) {
try {
Scanner scan = new Scanner(System.in);
System.out.print(prompt);
String tempString = "";
tempString = scan.nextLine();
scan.close();
char userChar = tempString.charAt(0);
return userChar;
} catch(Exception ex) {
System.out.println(ex.getMessage());
}
return 0;
}
代码循环由try / catch块引起,如scan.nextLine( )永远不会等待下一个输入。没有它,例外通常与找不到新行有关。我尝试了似乎适合其他人的while(scan.hasNextLine());但是,一旦输入的时间到来,它就永远不会脱离循环。我也不相信我正在绊倒每个人似乎都遇到麻烦的nextInt()问题。我将在下面发布整个类的代码:
The code loops due to the try/catch block, as scan.nextLine() never waits for the next input. Without it, the exception is typically related to not finding a new line. I've tried the while(scan.hasNextLine()) that seems to work for other people; however, once the time for input arrives, it never breaks out of the loop. I also don't believe I'm tripping up on the nextInt() issue that everyone seems to have troubles with. I'll post the code for the entire class below:
import java.util.Scanner;
import controller.Controller;
public class TUI {
private Controller controller;
public TUI() {
Controller controller = new Controller();
this.controller = controller;
}
public void run() {
boolean wantToQuit = false;
char userInput = 0;
System.out.println("Welcome to the Mart.");
do{
userInput = mainMenu();
if(isUserInputValid(userInput))
switch(userInput){
case 'a': addItem();
break;
case 'r': controller.removeItem();
break;
case 'i': controller.printInventory();
break;
case 'p': controller.customerPurchase();
break;
case 'w': controller.weeklyStock();
break;
case 'c': wantToQuit = true;
break;
}
else System.out.println("\nMainMenu");
} while(!(wantToQuit));
System.out.println("WolfMart is now closed. Thank you and good-bye.");
}
private boolean isUserInputValid(char userInput) {
char[] testSet = {'a', 'r', 'i', 'p', 'c', 'w'};
for(char currentChar : testSet) {
if(currentChar == userInput)
return true;
}
return false;
}
private char mainMenu() {
System.out.println();
controller.printInventory();
String mainMenuSelection = "What would you like to do: (a)dd item, (r)emove item, print (i)nventory, " +
"(p)urchase by customer, (c)lose store?\r\n";
char mainMenuInput = getUserChar(mainMenuSelection);
return mainMenuInput;
}
private char getUserChar(String prompt) {
try {
Scanner scan = new Scanner(System.in);
System.out.print(prompt);
String tempString = "";
tempString = scan.nextLine();
scan.close();
char userChar = tempString.charAt(0);
return userChar;
} catch(Exception ex) {
System.out.println(ex.getMessage());
}
return 0;
}
private int getUserInt(String prompt) {
Scanner scan = new Scanner(System.in);
int userInt = -1;
try {
System.out.print(prompt);
String input = scan.nextLine();
userInt = Integer.parseInt(input);
}
catch(NumberFormatException nfe) {
System.out.println("I did not recognize your command, please try again.");
}
scan.close();
return userInt;
}
private String getUserString(String prompt) {
Scanner scan = new Scanner(System.in);
String userString = null;
try{
System.out.print(prompt);
userString = scan.nextLine();
} catch(Exception ex)
{
System.out.println("I did not recognize your command, please try again.");
}
scan.close();
return userString;
}
private double getUserDouble(String prompt) {
Scanner scan = new Scanner(System.in);
double userDouble = -1.0;
try {
System.out.print(prompt);
String input = scan.nextLine();
userDouble = Double.parseDouble(input);
}
catch(NumberFormatException nfe) {
System.out.println("I did not recognize your command, please try again.");
}
scan.close();
return userDouble;
}
private void addItem() {
String itemName = "";
double price;
int quantity;
String namePrompt = "Enter the name of the item being added to the inventory: ";
String pricePrompt = "Enter the cost of " + itemName + ": ";
String quantityPrompt = "Enter the quantity of " + itemName + ": ";
itemName = getUserString(namePrompt);
price = getUserDouble(pricePrompt);
quantity = getUserInt(quantityPrompt);
controller.addItem(itemName, quantity, price);
}
}
推荐答案
正如我在,问题是每次你做这样的事情你关闭 System.in
:
As I stated in my comment, the problem is that you're closing System.in
each time you do something like this:
Scanner scan = new Scanner(System.in);
...
scan.close();
现在,看看
Now, look at the specification of Scanner.nextLine
-
NoSuchElementException
- 如果没有找到行 -
IllegalStateException
- 如果此扫描仪关闭
NoSuchElementException
- if no line was foundIllegalStateException
- if this scanner is closed
现在,因为扫描仪本身未关闭,将不会抛出 IllegalStateException
。相反,正如您之前提到的,抛出另一个例外,通常与找不到新行相关, - NoSuchElementException
。
Now, since the scanner itself is not closed, an IllegalStateException
will not be thrown. Instead, as you mentioned before, the other exception, "typically related to not finding a new line", -- NoSuchElementException
-- is thrown.
假设你正在使用JDK 7,你可以通过检查:
Presuming this you're using JDK 7, you can see how this works by examining Scanner.throwFor
:
if ((sourceClosed) && (position == buf.limit()))
throw new NoSuchElementException();
由于抛出异常,值 0
由 getUserChar
返回,然后在 run
循环中使用:
Since your exception is thrown, a value of 0
is returned by getUserChar
, which is then used in the run
loop:
do{
userInput = mainMenu();
if(isUserInputValid(userInput))
...
else System.out.println("\nMainMenu");
} while(!(wantToQuit));
由于输入无效,您陷入了循环打印\ nMainMenu \ n
。
Since the input is invalid, you're caught in a loop printing "\nMainMenu\n"
.
要解决此问题,请尝试使用单个扫描仪
并且不要关闭 System.in
; - )
To correct the issue, try to use a single Scanner
and don't close System.in
;-)
这篇关于Java Scanner.nextLine()不等待输入的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!