0

I simply have a program that must read a ssn (xxx-xx-xxxx) and determine if the given ssn is valid. I just need a way to check that the string only contains #'s and -'s.

import java.util.Scanner;
public class Prog7 {
  public static void main(String[] args) {

  Scanner input = new Scanner(System.in);
  System.out.print("Enter a SSN:");
  String ssn = input.next();

  if((ssn.substring(0, 4).indexOf('-') != 3) || (ssn.substring(4, 7).indexOf('-') != 2) || 
     (ssn.substring(ssn.length() - 5, ssn.length()).indexOf('-') != 0) ) {
     System.out.println(ssn + " is an invalid social security number");
  }
  else {
    System.out.println(ssn + " is a valid social security number");
  }

  }
}
Drizzles
  • 31
  • 1
  • 2
  • Seems a little over complicated. You could split the string around `-`s, check the substrings size and if they're #s. – ChiefTwoPencils Oct 17 '16 at 23:05
  • 1
    http://stackoverflow.com/questions/29764731/verifying-if-an-input-string-is-a-correct-social-security-number – Reimeus Oct 17 '16 at 23:10

3 Answers3

1

Regular expression representing xxx-xx-xxxx where x stands for digit can be written as \d\d\d-\d\d-\d\d\d\d (note: \ in String literals is special character, so if you want to use it as symbol and pass to regex engine you will need to escape it, so each \d needs to be written as "\\d").

Now you can simply use yourString.matches(regex) to see if regex matches whole yourString

So simple

String ssn = input.next();

if(ssn.matches("\\d\\d\\d-\\d\\d-\\d\\d\\d\\d")){
    //
}

should work fine. You can also reduce repetition with {n} to represent amount like instead of \d\d\d you can write \d{3}.

Also lets not forget that Scanner supports regex. So you can simply use hasNext(regex) to check if next token can be matched by regex. If it is not simply consume it with next() and ask for new one, like

System.out.print("Enter a SSN:");
while(!input.hasNext("\\d{3}-\\d{2}-\\d{4}")){
    String invalid = input.next();
    System.out.print(invalid + " is not valid SSN. Please try again:");
}
//outside this loop we are sure that valid SSN was provided 
String ssn = input.next();
Pshemo
  • 118,400
  • 24
  • 176
  • 257
0

Use a regular expression:

String ssn = input.next();
String pattern = "[0-9]{3}-[0-9]{2}-[0-9]{4}";
Pattern p = Pattern.compile(pattern);

Matcher m = p.matcher(ssn);
if (m.find( )) {
    System.out.println(ssn + " is an invalid social security number");
}else{
    System.out.println(ssn + " is a valid social security number");
}
Dez
  • 5,427
  • 7
  • 40
  • 49
0

And if you hate regex as much as I do, you could also iterate through characters comparing to ASCII values.

public class HelloWorld{

 public static void main(String []args){
    System.out.println("Test A: " + checkSSN("123-45-6789"));
    System.out.println("Test B: " + checkSSN("12a-45-6789"));
    System.out.println("Test C: " + checkSSN("123-4"));
    System.out.println("Test D: " + checkSSN("123-45-20303"));
 }

 public static boolean checkSSN(String ssn) {
     int count = 0;
     for (char c : ssn.toCharArray()) {
         if (count == 3 || count == 6) {
             if (c != '-') {
                 System.out.println("Character" + c + "Not a dash, returning false");
                 return false;
             } 
         } else if (c < '0' || c > '9') {
             System.out.println("NaN, return false");
             return false;
         }
         count++;
     }
     if (count != 11) {
         System.out.println("Doesn't meet length criteria");
         return false;
     }
     return true;
 }

}

Ben Harris
  • 1,682
  • 3
  • 15
  • 24
  • Avoid [magic numbers](http://stackoverflow.com/questions/47882/what-is-a-magic-number-and-why-is-it-bad). Instead of 45 simply use `'-'`, instead of 48 you can write `'0'`, and `'9'` for 57. – Pshemo Oct 17 '16 at 23:17
  • This is true. Thanks! – Ben Harris Oct 17 '16 at 23:18
  • I don't see ASCII anywhere in here. `char` is a UTF-16 code unit. All of the expected characters are one UTF-16 code unit so comparison with literal `char` values as you have done is appropriate. – Tom Blodget Oct 17 '16 at 23:34