1

Im trying to give the user the opportunity to repeat an input after introducing something that has produced an error but something is not working because once the err is caught the try stuff is not executed again, instead it goes directly to the catch stuff generating an eternal cicle. Here is my code:

while (err==1){
    err=0;
    try{
        dim = keyboard.nextInt();
    } catch(Exception e){
        System.out.println("Oops! What you entered is not an integer.");
        err=1;
    }
}
Sergey Kalinichenko
  • 714,442
  • 84
  • 1,110
  • 1,523
Gabriel
  • 13
  • 4

3 Answers3

5

When you enter a non-integer the Scanner call to nextInt() doesn't consume the non-integer. You need to call keyboard.next() (or keyboard.nextLine()) to consume it. Something like,

try {
    dim = keyboard.nextInt();
} catch (Exception e) {
    System.out.printf("%s is not an integer.%n", keyboard.next());
    err = 1;
}
Elliott Frisch
  • 198,278
  • 20
  • 158
  • 249
  • Thanks man! That works perfect. Anyway, I still don't know why if I'm calling "nextInt()" it returns the last input or err. I don't know how the class Scanner works but I was sure that every time you call "nextInt" it was cleaning its buffer... Thanks anyway! – Gabriel Feb 06 '15 at 05:32
  • @Gabriel Because the error is that there isn't an `int`. You say give me an `int` and the Scanner says there isn't one (there's a `String` waiting). Then you start the loop again, and say give me an `int` and the Scanner says... – Elliott Frisch Feb 06 '15 at 05:34
  • Sound good! But, when you say to the object "give me an int" you first enter some string in the console that I assume it goes directly to the objetc buffer after pressing enter... so why in my case that step doesn't exist and goes directly to ask for a int in the current buffer? – Gabriel Feb 06 '15 at 05:45
  • It does go directly into the `Scanner` (the object buffer)... and it doesn't leave until you read it out successfully... I have a `String`... you say give me an `int`... I say there isn't an `int`... but, there is still the `String`. – Elliott Frisch Feb 06 '15 at 05:47
  • I'am wondering: if after calling the object keyword with the statement "nextInt" the buffer is not flushed then why if I call this function for example twice in a row I can get the two inputs separately without calling "next()". You know what I mean? – Gabriel Feb 06 '15 at 05:54
  • You aren't getting two inputs separately. Your getting the same input... let's say you input "Fred". Then you say give me an `int`, the Scanner throws an error because "Fred" isn't an `int`. Then you start the loop over, and say give me an `int`... the Scanner throws the same error because "Fred" hasn't changed into an `int`. It doesn't throw "Fred" away. And it doesn't wait for more input from the user. It says "Fred" isn't an `int`. – Elliott Frisch Feb 06 '15 at 05:56
  • Yep, I think I get that part perfectly :) What I mean in the last comment was, for example: number1=keyword.nextint(); number2=keyword.nextint(); I can perfectly get the two numbers whitout having to clearing the buffer. Why? – Gabriel Feb 06 '15 at 06:04
  • 1
    Are you entering `int`(s)? If you say give me an `int`, and there is an `int`; the Scanner says here is your `int` and clears the buffer because it *delivered* an `int`. – Elliott Frisch Feb 06 '15 at 06:05
  • Applause! I can't say I'm an expert in terms of getting inputs through Scanner but I get the important idea of: "Keep asking me but I'm not cleanin my buffer until I can give you exactly what you are looking for. Okay, if you whant me to clean it just say next and nothing happened here". Thank you very much! – Gabriel Feb 06 '15 at 06:12
1

You are not clearing/flushing the scanner buffer after each user input.

  • Use keyboard.nextLine() just before the end of while loop(after the catch block)

    OR

  • Declare the scanner object inside the while loop itself Scanner keyboard = new Scanner(System.in);

See this

Cheers!

Community
  • 1
  • 1
nalinc
  • 7,375
  • 24
  • 33
0

The problem is with the input.nextInt() command it only reads the int value. It would be even better, if you read the input through Scanner#nextLine and convert your input to integer using Integer#parseInt(String) method.

This does work for me.

 public static void main(String[] args) {
    int err = 1;
    Scanner keyboard = new Scanner(System.in);
    while (err == 1) {
        err = 0;
        try {
            int dim = Integer.parseInt(keyboard.nextLine());
            System.out.println("done.. exit");
        } catch (Exception e) {
            System.out.println("Ups! What you entered is not an integer.");
            err = 1;
        }
    }
}

output

dd
Ups! What you entered is not an integer.
23
done.. exit

next() can read the input only till the space. It can't read two words separated by space. Also, next() places the cursor in the same line after reading the input.

nextLine() reads input including space between the words (that is, it reads till the end of line \n). Once the input is read, nextLine() positions the cursor in the next line.

for reading the entire line you can use nextLine()

Ankur Singhal
  • 26,012
  • 16
  • 82
  • 116
  • Thanks! It works because when the cicle starts again you call again the class Scanner. Like Elliott Frisch said I think this is more correct to use the keyboard.next() to clean the buffer. – Gabriel Feb 06 '15 at 05:26