3

i'm trying to read long types from a text file with using readLine() method of BufferedReader class and then i parse the first token (which is long type number) with using StringTokenizer but i'm facing with an exception error which is java.lang.NumberFormatException

this is an example of my text file;

2764841629  Quaroten Ilen
1398844030  Orden Nenama
1185252727  Inja Nenaptin
2370429126  Quaren Inaja
1502141743  Otin Una
1993687334  Quarwennaja Nenoten
1015934104  Polen Meritna
2363674760  Otja Ie
1904629749  Neninin Ordja
3047965620  Algnaja Nenja

here is the code i read from a text file and assing the long value to my long variable

private void registerData() throws FileNotFoundException{
    try {

        String regPatName;
        String regPatSurname;
        long regPatID;


        FileInputStream fis = new FileInputStream("src\\assignment_3\\injuredPersonList.txt");
        BufferedReader reader = new BufferedReader(new InputStreamReader(fis));

        String line;

        while( ( line = reader.readLine() ) != null) {

            StringTokenizer st = new StringTokenizer(line, " ");

            while(st.hasMoreTokens()){

                regPatID = Long.parseLong(st.nextToken());
                regPatName = st.nextToken();
                regPatSurname = st.nextToken();

                Patient regPatient = new Patient(regPatName, regPatSurname, regPatID);
                hashMethod(regPatient);
            }

        }
    } catch (IOException ex) {
        Logger.getLogger(personTest.class.getName()).log(Level.SEVERE, null, ex);
    }


}

private void hashMethod(Patient regPatient){

    Long idPat = new Long(regPatient.getPatientID());
    int keyID;

    keyID = (int) Math.sqrt(Integer.parseInt(idPat.toString().substring(0, 5) + idPat.toString().substring(5, 10))) % (50000);

    System.out.println(keyID);

}

and finally this the error which i'm facing;

Exception in thread "AWT-EventQueue-0" java.lang.NumberFormatException: For input string: "2481765933   Otna"
    at java.lang.NumberFormatException.forInputString(NumberFormatException.java:48)
    at java.lang.Long.parseLong(Long.java:419)
    at java.lang.Long.parseLong(Long.java:468)
    at assignment_3.personTest.registerData(personTest.java:58)
    at assignment_3.personTest.<init>(personTest.java:33)
    at assignment_3.personTest$1.run(personTest.java:161)
    at java.awt.event.InvocationEvent.dispatch(InvocationEvent.java:209)
    at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:641)
    at java.awt.EventQueue.access$000(EventQueue.java:84)
    at java.awt.EventQueue$1.run(EventQueue.java:602)
    at java.awt.EventQueue$1.run(EventQueue.java:600)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.security.AccessControlContext$1.doIntersectionPrivilege(AccessControlContext.java:87)
    at java.awt.EventQueue.dispatchEvent(EventQueue.java:611)
    at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:269)
    at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:184)
    at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:174)
    at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:169)
    at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:161)
    at java.awt.EventDispatchThread.run(EventDispatchThread.java:122)

i will be very appreciated if you can help me and also thanks anyway.

quartaela
  • 2,579
  • 16
  • 63
  • 99

3 Answers3

4

Clearly you're trying to parse a non-numeric string, the stack trace shows it: 2481765933 Otna. You should split the input and parse the numeric part, something like this:

String[] data = line.split("\\s+");
regPatID = Long.parseLong(data[0]);
regPatName = data[1];
regPatSurname = data.length == 3 ? data[2] : "";

The above is much simpler than using StringTokenizer. In fact, the usage of StringTokenizer is discouraged, practically deprecated - nowadays, the preferred way to parse a string is either using the split() method for simple cases or the Scanner class for complex cases.

Community
  • 1
  • 1
Óscar López
  • 232,561
  • 37
  • 312
  • 386
  • but i use this parsing method many times when i read in integer value like when i have line "21321 otna". i guess the only problem is about long types – quartaela Mar 10 '12 at 16:07
4

You probably have a tab character instead of spaces to separate your fields. Add the tab to your set of delimiters (" \t").

Also, always close your streams and readers in a finally block (only the outermost one must be closed: closing the BufferedReader will close the InputStreamReader, which will close the FileInputStream).

JB Nizet
  • 678,734
  • 91
  • 1,224
  • 1,255
  • thanks for suggestion but nothing changed except it throws java.lang.NumberFormatException: For input string: "2481765933". input string doesnt contain the other token anymore – quartaela Mar 10 '12 at 16:09
  • This String is a valid long representation, and I parse it without any problem. Are you sure it doesn't contain a bizarre character that would look like an ASCII digit but isn't one? – JB Nizet Mar 10 '12 at 16:15
  • well it gives the error when it reads the first line. i check the first one thousand lines for if it contains a bizarre character but not. – quartaela Mar 10 '12 at 16:19
  • Add this snippet to your code: `String s = st.nextToken(); for (char c : s.toCharArray()) {System.out.print(" " + (int) c);} System.out.println(); regPatID = Long.parseLong(s);` and tell us what is printed just before the exception is thrown. – JB Nizet Mar 10 '12 at 16:27
  • it gives "50 52 56 49 55 54 53 57 51 51" and `exception is Exception in thread "AWT-EventQueue-0" java.lang.NumberFormatException: For input string: "Otna"` – quartaela Mar 10 '12 at 16:36
  • and this is my first line `2481765933 Otna Orda` – quartaela Mar 10 '12 at 16:37
  • You're trying to parse "Otna" as a long now. Are you sure you replaced `regPatID = Long.parseLong(st.nextToken();` with `regPatID = Long.parseLong(s);`? – JB Nizet Mar 10 '12 at 16:51
  • i guess we are looking wrong place cause i tried just reading and printing the numbers in txt and it worked. so there is no problem about parsing reading etc. but in main code which i posted i pass an object to hashMethod() i guess there is the problem but i couldnt find it everything seems ok_? – quartaela Mar 10 '12 at 17:04
  • So, if I understand correctly, adding the tab as a delimiter fixed the original problem, but you now have an exception in another part of the code. – JB Nizet Mar 10 '12 at 17:06
  • i'm sure the problem is in `hashMethod(Patient regPatient)` cause when i delete the code which i call `hashMethod()` everything works perfect! – quartaela Mar 10 '12 at 17:07
  • Then investigate. Read the exception message carefully, and use a debugger, or traces in the code, to discover what is wrong. – JB Nizet Mar 10 '12 at 17:07
  • well finally i realized i'm using Integer parser in hashMethod and this stupid thing took my 2 hours to realize... pfff. by the way thanks for your help. – quartaela Mar 10 '12 at 17:12
3

You are using the wrong delimiter (" ") since your text file may contain more than one space character between tokens. StringTokenizer is a legacy class, don't use it unless you have a good reason to. String.split() should suffice:

String[] result = line.split("\\s+");
regPatID = Long.parseLong(result[0]);
regPatName = result[1];
regPatSurname = result[2];

But I think that Scanner is the best fit for your problem:

// Java 7 try-with-resources synthax.
// If you are using Java <=6, declare a finally block after the catch 
// to close resources.
try (InputStream myFile = ClassLoader.getSystemResourceAsStream("MyTextFile.txt");
        Scanner sc = new Scanner(myFile)) {

    while (sc.hasNext()) {
        regPatID = sc.nextLong();
        regPatName = sc.next();
        regPatSurname = sc.next();

        System.out.printf("%d - %s %s\n", regPatID, regPatName, regPatSurname);
    }

} catch (Exception e) {
    // Do something about exceptions
}

Both versions correctly parses your example input.

Here is a third fully working Java 6 Version.

Anthony Accioly
  • 21,918
  • 9
  • 70
  • 118
  • well when i printout the "result[0]" and "regPatID" it prints the true value but again i'm facing this same stupid error. i mean it assignes truly but i dont know why i'm taking same error again. – quartaela Mar 10 '12 at 16:24
  • mate i solved the problem 5 minutes ago which is about i was using `Integer.parseInt()` in `hashMethod()` as you can see in my question. and yes this works correctly as well and thanks for your help – quartaela Mar 10 '12 at 17:14
  • Hi quartaela, I'm glad to be of service, since you have figured it out, you should accept @JB Nizet or Óscar López answers to reward them by helping you with your original question ;). – Anthony Accioly Mar 10 '12 at 17:19