4

I am making a simple program that lets you add the results of a race, and how many seconds they used to finish. So to enter the time, I did this:

int time = Integer.parseInt(JOptionPane.showInputDialog("Enter seconds"));

So my question is, how can I display an error message to the user if he enters something other than a positive number? Like a MessageDialog that will give you the error until you enter a number.

ddavison
  • 28,221
  • 15
  • 85
  • 110
Misoxeny
  • 93
  • 2
  • 3
  • 10
  • 3
    @PradeepSimha You have a problem. You use regular expressions. Now you have two problems. – tckmn Jan 16 '13 at 13:51
  • Please add more tags. Are you using Swing? – gaborsch Jan 16 '13 at 13:51
  • 3
    If it is an integer number of seconds, offer the user a `JSpinner` with a `SpinnerNumberModel` as seen in [this answer](http://stackoverflow.com/questions/9344708/jcombobox-to-list-age/9345991#9345991). – Andrew Thompson Jan 16 '13 at 13:52
  • Just run your code and enter some invalid input. You will get the exception. So what you have to do is handle your exception. – Arpit Jan 16 '13 at 13:57
  • again use JFormattedTextField or JSpinner instead, why to reinvent the wheel – mKorbel Jan 16 '13 at 14:09
  • Thanks for the answers, I got it working with Doorknob's suggestion. However, if I click "Cancel" or the X I also get the "Enter a number"-message. I only want it to show if I actually enter a number, cause obviously sometimes I want to exit the whole adding process instead of being forced to finish it. – Misoxeny Jan 16 '13 at 14:40
  • 1
    If you need that, you can't immediately parse; you must first check for zero length. – Marko Topolnik Jan 16 '13 at 14:49
  • wheel ! commons-langs org.apache.commons.lang.math.NumberUtils.isNumber(String) – farmer1992 Jan 16 '13 at 14:00
  • OP wants `isDigits`, in fact. – Marko Topolnik Jan 16 '13 at 14:11

4 Answers4

11
int time;
try {
    time = Integer.parseInt(JOptionPane.showInputDialog("Enter seconds"));
} catch (NumberFormatException e) {
    //error
}

Integer.parseInt will throw a NumberFormatException if it can't parse the int. If you just want to retry if the input is invalid, wrap it in a while loop like this:

boolean valid = false;
while (!valid) {
    int time;
    try {
        time = Integer.parseInt(JOptionPane.showInputDialog("Enter seconds"));
        if (time >= 0) valid = true;
    } catch (NumberFormatException e) {
        //error
        JOptionPane.showConfirmDialog("Error, not a number. Please try again.");
    }
}
tckmn
  • 57,719
  • 27
  • 114
  • 156
  • Your elaborate code now does exactly the same as `input.matches("\\d+")`. I really don't see the angle on how this simplest of regexps has more problems than your elaborate scheme which involves exceptions for regular flow control, a clear code smell. – Marko Topolnik Jan 16 '13 at 14:09
  • 1
    @MarkoTopolnik For one, my "elaborate" code is 11 lines, four of which actually do something. Also, with your method, you would also have to add a `while` loop, new `input` variable, etc. Elaborate-ness aside, I think this is a perfectly valid way to teach new Java programmers about exceptions and such. – tckmn Jan 16 '13 at 14:12
  • OK, so the core part is `try {return Integer.parseInt(input) >= 0;} catch (NumberFormatException e) {return false; }` against `return input.matches("\\d+");`. And teaching people to use exceptions (unchecked, no less!) for regular flow control is just an example of bad teaching. Teaching them not to use regular expressions for string validation is yet another example of the same. – Marko Topolnik Jan 16 '13 at 14:15
  • 1
    @MarkoTopolnik Given the apparent intent to get an integer that fits in a Java int, you would need a bit more than input.matches("\\d+"). It would accept a string of 100 digits. – Patricia Shanahan Jan 16 '13 at 14:57
  • +1 @PatriciaShanahan Point taken. It is easy to fix, though, for example `\\d{1,3}`, which goes even a step further by validating the number range. – Marko Topolnik Jan 16 '13 at 15:02
2

Integer.parseInt Throws NumberFormatException when the parameter to Integer.parseInt is not a integer, Use try Catch and display required error message, keep it in do while loop as below

   int   time = -1;
   do{
       try{
            time = Integer.parseInt(JOptionPane.showInputDialog("Enter seconds"));
       }
       catch(NumberFormatException e){

       }
   }while(time<=0);
Fahad
  • 749
  • 6
  • 12
1

If JOptionPane.showInputDialog("Enter seconds") is not a valid number, you will be getting NumberFormatException.For positive number check, just check time >=0

Andrew Thompson
  • 168,117
  • 40
  • 217
  • 433
Renjith
  • 3,274
  • 19
  • 39
0

Depends on how you want to solve it. An easy way is to declare time as an Integer and just do:

Integer time;    
while (time == null || time < 0) {
    Ints.tryParse(JOptionPane.showInputDialog("Enter seconds"));
}

Of course that would require you to use google guava. (which contains a lot of other useful functions).

Another way is to use the above code but use the standard tryparse, catch the NumberFormatException and do nothing in the catch.

There are plenty of ways to solve this issue.

Or not reinvent the wheel and just use: NumberUtils.isNumber or StringUtils.isNumeric from Apache Commons Lang.

Jack Mans
  • 23
  • 1
  • 6