So i need help, i am trying to input a Y/N program but it is not accepting a big 'Y' or 'N'. Also another thing that i am trying to do is after pressing 'Y'/'y' i am trying to get the program to loop back to the code written above. Example a program that displays '123' and do i need to continue? Y/N, if entered yes it goes back up to restart the program from scratch. Please help me.
System.out.println("continue? Yes or no ");
char check = s.next().charAt(0);
while (check != 'y' && response != 'n')// corrected this part, however need help with restarting the loop back to the first line of code in a loop {
System.out.println("\nInvalid response. Try again.");
check = s.next().charAt(0);
} if ((check == 'n') || (check == 'N')) {
// I tried (check == 'n' || check == 'N')
System.out.println("Program terminated goodbye.");
System.exit(0);
} else if (check == 'y') {
//need help with restarting the loop back to the first line of code in a loop
}
I think this is what you are looking for.
char check;
Scanner scanner = new Scanner(System.in);
do
{
//your piece of code in here e.g.
System.out.println("Printed 123");
System.out.println("Do you wish to continue?[Y/y] or [N/n]");
choice = scanner.next().charAt(0);
}while (check =='Y' || check == 'y');
System.out.println("Program terminated goodbye.");
A do-while loop runs at least once before the condition is checked and so when a user enters either Y or y, then the condition will be true, meaning that they wish for the loop to run again. If the user enters any other value, then the condition will become false since choice is neither Y nor y and the loop will terminate.
Use String.equals() to compare the value of strings, == compares the strings in memory.
If you want to check without case-sensitive, you should convert the char to a String, then do s1.equalsIgnoreCase(s2);
So
while(true) {
System.out.println("Continue? [Y/N]");
char check_char = s.next().charAt(0);
String check = Character.toString(check_char);
while(check.equalsIgnoreCase("y") && !response.equalsIgnoreCase("n")) {
System.out.println("\nInvalid response. Try again.");
check = s.next().charAt(0);
}
if (check.equalsIgnoreCase("n")) {
System.out.println("Program terminated goodbye.");
System.exit(0);
}
}
For returning to the first line, I used a while loop that loops forever.
To the end if it is n then exits, otherwise it returns back to the first line of the loop.
Related
Can someone please advise why the inner loop of the code below will not exit?
I've added an inner loop to check if input from the user of of a particular value and if not prompts for the correct input. When debugging the code and passing in a value which should force the loop to end it doesn't although I can see the correct value in the variable:
while (finished.equalsIgnoreCase("n")) {
System.out.println("Enter a persons name");
names = in.nextLine();
writer.println(names);
System.out.println("Finished? (Y/N)");
finished = in.nextLine();
while( !finished.equalsIgnoreCase("y") || !finished.equalsIgnoreCase("n")) {
System.out.println("Invalid choice; (Y/N)");
finished = in.nextLine();
}
}
Every string is either not not equal to y or not equal to n. You probably meant to use the && operator:
while(!finished.equalsIgnoreCase("y") &&
!finished.equalsIgnoreCase("n")) {
// Code...
I'm having a problem handling exceptions. Honestly, I really don't understand how it works since I self study.
I'm working with a program where there would be a main menu with the following choices.
Odd/Even - asks an integer input from user and identify if it is an odd or even. Program would continuously ask for an integer input if the user keeps on giving character inputs. (I was able to do this but I keep on getting errors when I use br.readLine() in getting input. Pls see codes below. So I used the normal parsing. Since I didn't use Buffered Reader, I try to delete it but the Odd/Even program wouldn't handle the exception without it.)
Vowel/Consonant - asks the user for a character input and identify if it is a vowel or a consonant. Program should reject integer inputs. The program I made with the codes below doesn't reject integer inputs. I tried searching for answers but I can't find one.
Please ignore for now.
My problem/s involve/s the following questions.
1. Why doesn't the program Odd/Even handle the NumberFormat exception whenever I try to delete the BufferedReader line even though it wasn't used in the whole program?
How can I reject integer inputs for the Vowel/Consonant program?
Here is a video when I tried to run the program.
http://tinypic.com/r/24ou9kz/9
When I exit the program, the console shows this.
Exception in thread "main" java.lang.NumberFormatException: null at
java.lang.Integer.parseInt(Unknown Source) at
java.lang.Integer.parseInt(Unknown Source)
import javax.swing.JOptionPane;
import java.io.*;
import java.util.InputMismatchException;
public class DoWhileIf {
public static void main(String[] args) throws Exception {
// TODO Auto-generated method stub
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
String input;
int choice, num = 0;
char again = 0;
boolean err = true;
do {
input = JOptionPane.showInputDialog("Menu\n[1] Odd/Even\n[2] Vowel/Consonant\n[3] CQM\n[4] Fuel Efficiency\n[5] Scholarship\n[6] Exit program.\n\nEnter Choice.");
choice = Integer.parseInt(input);
if (choice == 1) {
do {
do {
try {
input = JOptionPane.showInputDialog("Input an integer : ");
num = Integer.parseInt(input);
err = false;
} catch (NumberFormatException o) {
JOptionPane.showMessageDialog(null,"Error!");
err = true;
}
} while (err);
if (num % 2 == 0) {
JOptionPane.showMessageDialog(null,"Even.");
}
else {
JOptionPane.showMessageDialog(null,"Odd.");
}
do {
input = JOptionPane.showInputDialog("Try again? Press Y for yes or N to go back to main menu.");
again = input.charAt(0);
} while (again != 'Y' && again != 'y' && again !='N' && again !='n');
} while (again == 'Y' || again == 'y');
}
if (choice == 2) {
char letter = 0;
do {
do {
try {
input = JOptionPane.showInputDialog("Character : ");
letter = input.charAt(0);
err = false;
} catch (InputMismatchException a) {
JOptionPane.showMessageDialog(null,"Error!");
err = true;
}
} while (err);
if (letter == 'a' || letter == 'A' || letter == 'e' || letter == 'E' || letter == 'i' || letter == 'I' || letter == 'o' || letter == 'O' || letter == 'u' || letter == 'U') {
JOptionPane.showMessageDialog(null,"Vowel");
}
else {
JOptionPane.showMessageDialog(null,"Consonant");
}
do {
input = JOptionPane.showInputDialog("Try again? Press Y for yes or N to go back to main menu.");
again = input.charAt(0);
} while (again != 'Y' && again != 'y' && again !='N' && again !='n');
} while (again == 'Y' || again == 'y');
}
} while (choice <= 0 || choice > 6 || again == 'N' || again == 'n');
}
Why doesn't the program Odd/Even handle the NumberFormat exception whenever I try to delete the BufferedReader line even though it wasn't
used in the whole program?
I am not able to duplicate this problem. I removed the BufferedReader and option #1 works the same as it did before. I entered integer values, special characters, letters, spaces and it works fine.
How can I reject integer inputs for the Vowel/Consonant program?
You could modify your else condition from this:
else {
JOptionPane.showMessageDialog(null,"Consonant");
}
to this:
else if(Character.isLetter(letter)){
JOptionPane.showMessageDialog(null,"Consonant");
}
else{
JOptionPane.showMessageDialog(null,"Error! You must enter a valid letter.");
}
When I exit the program, the console shows this.
Exception in thread "main" java.lang.NumberFormatException: null at ...
Regarding the NumberFormatException you're seeing, I'm guessing you're pressing the Cancel button on the dialog. When you press cancel the variable input receives the value null. When you try to parse null as an integer it fails and throws the exception:
Exception in thread "main" java.lang.NumberFormatException: null
at java.lang.Integer.parseInt(Unknown Source)
at java.lang.Integer.parseInt(Unknown Source)
at exception.DoWhileIf.main(DoWhileIf.java:18)
Line 18 is this line: choice = Integer.parseInt(input);
Notice how the exception told us - java.lang.NumberFormatException: null which tells us that the parameter being passed to the parseInt method is null.
Lastly some additional thoughts for you to consider:
Whenever you get input from the user you must account for all the possibilities somehow. For example when you have code like this:
letter = input.charAt(0);
you're not accounting for the possibility that the input could be null or empty in which case this logic will throw an exception.
A concrete example is when the user clicks Cancel on the dialog that asks whether they want to try again:
input = JOptionPane.showInputDialog("Try again? Press Y for yes or N to go back to main menu.");
When the user clicks Cancel on this dialog the same thing happens that I described above regarding the NumberFormatException - input becomes null. If you try to use input like this:
again = input.charAt(0);
it will fail with the exception:
Exception in thread "main" java.lang.NullPointerException
because you can't invoke a method on a null.
Another example is when the user enters nothing at the main menu but simply presses OK. The result is this exception:
Exception in thread "main" java.lang.NumberFormatException: For input string: ""
This happens because input was set to an empty string and parseInt does not know how to convert empty string into an integer value.
Another item I want to bring up is that you're using this same piece of code over and over again. Whenever you have code you want to reuse you should not copy and paste it but instead create a method, object, or other construct so that you can refer to it.
do {
input = JOptionPane.showInputDialog("Try again? Press Y for yes or N to go back to main menu.");
again = input.charAt(0);
} while (again != 'Y' && again != 'y' && again !='N' && again !='n');
Breaking up your logic into smaller more manageable pieces will help you to debug, test, and maintain your code more easily.
Another point I want to touch on regarding this same block of logic is that you're using the same kind of dialog to ask for many different kinds of input. Since you're using a GUI dialog, you could use a dialog that is better suited to your task such as one that asks the user to press either a Yes button or No button.
You can learn more about different kinds of dialogs by reading the How to Make Dialogs Tutorial
Here is an example of how you could create a more friendly dialog:
/**
* Asks the user if they want to try something again and
* returns a boolean representing the user's response.
* #return true if the user answers Yes, false otherwise.
*/
private static boolean promptToRepeatSelectedOption(){
int n = JOptionPane.showOptionDialog(null,
"Try again?",
"Repeat Selection",
JOptionPane.YES_NO_OPTION,
JOptionPane.QUESTION_MESSAGE,
null,
null,
null);
return n == JOptionPane.YES_OPTION;
}
The above method, when invoked, will create and display a dialog with two buttons - Yes and No - and the user will have to select one of them or close the dialog. The logic simply looks for if the user said Yes (by clicking the Yes button) and returns true when that is the case. If the user closes the dialog or chooses the No option the method returns false simply because either of those two scenarios will cause the n == JOptionPane.YES_OPTION comparison to result in a value of false.
You can replace your entire loop with a call to this method like this:
First, define a variable to hold the user's response.
boolean repeat = false;
Then invoke the method and set the variable to its result:
repeat = promptToRepeatSelectedOption();
Now replace the outer loop condition
while (again == 'Y' || again == 'y');
with this: while (repeat);
and finally replace part of the outermost loop condition
again == 'N' || again == 'n'
with this: !repeat
One final thought is that you're using very general error messages when the user enters something incorrect or invalid:
JOptionPane.showMessageDialog(null, "Error!");
It's always better to explain to the user a little bit about what they did wrong so that they know how to avoid the error next time. You should probably consider adding more detail to your error messages.
Hope this helps!
I am working on a java program. Right now everything is totally working, and all my functionality is there. However, the part I am stuck on is how to exit out of the program in a do-while loop. I must be getting the syntax wrong.
Basically, I set a switch done which reacts to a user's input. Right now, it's working and loops through the program, but it does not exit if I say "no" to continuing.
Here is the part of the code this is happening:
public void main() {
String userInput;
boolean done = true;
Scanner keyboard = new Scanner(System.in);
do {
System.out.println("Welcome to Hangman!");
System.out.println("Do you want to play?");
userInput = keyboard.next();
if (userInput.equals("Yes") || userInput.equals("yes") || userInput.equals("y") || userInput.equals("Y")) {
done = false;
} else if (userInput.equals("n") || userInput.equals("no") || userInput.equals("NO") || userInput.equals("No")) {
done = true;
}
while (!done) {
System.out.println(getDisguisedWord());
System.out.println("Guess a letter: ");
String guess = keyboard.next();
makeGuess(guess);
if (gameOver()) {
String ui;
System.out.println("Do you want to play again?");
ui = keyboard.next();
if (ui.equals("Yes") || ui.equals("yes") || ui.equals("y") || ui.equals("Y")) {
done = false;
} else {
done = true;
}
}
}
} while(done);
}
any tips on how I could handle this better?
Your problem isn't what you think it is. To compare Strings, you need to use their built-in equals() method: ui.equals("Y"). Using == to compare them will always return false. For more information, see How do I compare strings in Java?.
Also, you need to flip your done = true and done = false statements (if the user says yes to playing again, they aren't done yet).
Finally, I would recommend changing your keyboard.next() calls to keyboard.nextLine() calls, or else you may run into weird issues, especially if the user enters input that includes whitespace.
EDIT: I noticed some more issues. You're while loop should be while(!done) instead of while(done). Also, I would get rid of your do-while loop, because the while loop is already allowing the user to play as many times as they want, so it is unnecessary.
boolean flag = true;
Scanner sc = new Scanner(System.in);
do{
System.out.println("***********************************************************");
System.out.println("Welcome to the School Admissions App !!! Press X for exit");
System.out.println("***********************************************************");
System.out.println("Enter the Student Name: ");
String student_name=sc.next();
System.out.println("press y to use this application again. press x to exit from this application ");
String input_user=sc.next();
if(input_user.equalsIgnoreCase("y")){
flag=true;
}else{
flag=false;
System.out.println("Thanks for using it.");
}
}while(flag);
U should use equals method for comparing string value in if statment. ui.equals("yes").
Here's my code:
public boolean isConsonant(char x){
if (!Character.isLetter(x)){
System.out.print ("What you have entered cannot be a consonant or vowel.");
return false;
}
return (x != 'a' && x != 'e' && x != 'i' && x != 'o' && x != 'u');
}
The problem I'm having is the first if statement. I call the isConsonant method multiple times in the code after this and depending on the return calue (true or false) the code does some action.
The problem is that I don't want the method to continue at all if the char isn't a letter. I want the program to end. What I tried to do is write another method that looked like this:
public voidisNotLetter(char x)
if (!Character.isLetter(x){
System.out.println("What you have entered cannot be a consonant or vowel.");
}
This is where I'm stuck. I don't know what I can put in that method that will stop the program from running and just print that statement to the user. I thought about throwing an IllegalArgumentException, but that's not technically true since the argument is valid but just isn't what I want.
If you want to "stop the program from running and just print that statement to the user", this might help :
if (!Character.isLetter(x)){
System.out.print ("What you have entered cannot be a consonant or vowel.");
System.exit(0); //This would terminate the execution if the condition is met
}
More details here. Hope it helps.
You can try nesting if statements.
if(isLetter(input)){
if(isConsonant(input)
//input is consonant
else
//input is not consonant
}else{
//input is not letter
}
Everything of my guessing game is alright, but when it gets to the part of asking the user if he/she wants to play again, it repeats the question twice. However I found out that if I change the input method from nextLine() to next(), it doesn't repeat the question. Why is that?
Here is the input and output:
I'm guessing a number between 1-10
What is your guess? 5
You were wrong. It was 3
Do you want to play again? (Y/N) Do you want to play again? (Y/N) n
Here is the code:(It is in Java)
The last do while loop block is the part where it asks the user if he/she wants to play again.
import java.util.Scanner;
public class GuessingGame
{
public static void main(String[] args)
{
Scanner input = new Scanner(System.in);
boolean keepPlaying = true;
System.out.println("Welcome to the Guessing Game!");
while (keepPlaying) {
boolean validInput = true;
int guess, number;
String answer;
number = (int) (Math.random() * 10) + 1;
System.out.println("I'm guessing a number between 1-10");
System.out.print("What is your guess? ");
do {
validInput = true;
guess = input.nextInt();
if (guess < 1 || guess > 10) {
validInput = false;
System.out.print("That is not a valid input, " +
"guess again: ");
}
} while(!validInput);
if (guess == number)
System.out.println("You guessed correct!");
if (guess != number)
System.out.println("You were wrong. It was " + number);
do {
validInput = true;
System.out.print("Do you want to play again? (Y/N) ");
answer = input.nextLine();
if (answer.equalsIgnoreCase("y"))
keepPlaying = true;
else if (answer.equalsIgnoreCase("n"))
keepPlaying = false;
else
validInput = false;
} while (!validInput);
}
}
}
In your do while loop, you don't want the nextLine(), you just want next().
So change this:
answer = input.nextLine();
to this:
answer = input.next();
Note, as others have suggested, you could convert this to a while loop. The reason for this is that do while loops are used when you need to execute a loop at least once, but you don't know how often you need to execute it. Whilst it's certainly doable in this case, something like this would suffice:
System.out.println("Do you want to play again? (Y/N) ");
answer = input.next();
while (!answer.equalsIgnoreCase("y") && !answer.equalsIgnoreCase("n")) {
System.out.println("That is not valid input. Please enter again");
answer = input.next();
}
if (answer.equalsIgnoreCase("n"))
keepPlaying = false;
The while loop keeps looping as long as "y" or "n" (ignoring case) isn't entered. As soon as it is, the loop ends. The if conditional changes the keepPlaying value if necessary, otherwise nothing happens and your outer while loop executes again (thus restarting the program).
Edit: This explains WHY your original code didn't work
I should add, the reason your original statement didn't work was because of your first do while loop. In it, you use:
guess = input.nextInt();
This reads the number off the line, but not the return of the line, meaning when you use:
answer = input.nextLine();
It immediately detects the leftover carriage from the nextInt() statement. If you don't want to use my solution of reading just next() you could swallow that leftover by doing this:
guess = input.nextInt();
input.nextLine();
rest of code as normal...
The problem really lies in a completely different segment of code. When in the previous loop guess = input.nextInt(); is executed, it leaves a newline in the input. Then, when answer = input.nextLine(); is executed in the second loop, there already is a newline waiting to be read and it returns an empty String, which activates the final else and validInput = false; is executed, to repeat the loop (and the question).
One solution is to add an input.nextLine(); before the second loop. Another is to read guess with nextLine() and then parse it into an int. But this complicates things as the input could not be a correct int. On a second thought, the code already presents this issue. Try entering a non-numeric response. So, define a function
public static int safeParseInt(String str) {
int result;
try {
result= Integer.parseInt(str) ;
} catch(NumberFormatException ex) {
result= -1 ;
}
return result ;
}
And then replace your first loop with:
do {
validInput= true ;
int guess= safeParseInt( input.nextLine() ) ;
if( guess < 1 || guess > 10 ) {
validInput= false ;
System.out.print("That is not a valid input, guess again: ");
}
} while( !validInput );
PS: I don't see any problem with do-while loops. They are part of the language, and the syntax clearly indicates that the condition is evaluated after the body is executed at least one time. We don't need to remove useful parts of the language (at least from practice) just because others could not know them. On the contrary: if we do use them, they will get better known!
validInput = false;
do {
System.out.print("Do you want to play again? (Y/N) ");
answer = input.next();
if(answer.equalsIgnoreCase("y")){
keepPlaying = true;
validInput = true;
} else if(answer.equalsIgnoreCase("n")) {
keepPlaying = false;
validInput = true;
}
} while(!validInput);
I changed the coding style as I find this way more readable.
Your problem is that nextInt will stop as soon as the int ends, but leaves the newline in the input buffer. To make your code correctly read the answer, you'd have to enter it on the same line as your guess, like 5SpaceYReturn.
To make it behave more than one would expect, ignore the first nextLine result if it contains only whitespace, and just call nextLine again in that case without printing a message.
I believe the output of input.nextLine() will include the newline character at the end of the line, whereas input.next() will not (but the Scanner will stay on the same line). This means the output is never equal to "y" or "n". Try trimming the result:
answer = input.nextLine().trim();