-2

My code is supposed to read a file line by line, to put each one in a string array named: tuples, (tuples=ligne.split(" "); ) and then add this tuples to an arraylist, one line read = one element of the arraylist. Unfortunately, my code doesn't work! My buffered reader throws a NullPointerException in my loop! Error returned in the ExtractFile() method, line 120: tuples= ligne.split(" ");

File file = new File("Department.txt");

BufferedReader in;
PrintWriter out;
String ligne;
int nbCols; //number of metadatas in my file.txt  

String metadata[] = new String[nbCols];
String[] tuples = new String[nbCols];//1ere case indique num ligne

ArrayList<String[]> itemset = new ArrayList<String[]>();

public ArrayList ExtractionFile () {
    try {
        int i = 1;
        in = new BufferedReader(new FileReader(file));
        while ((ligne = in.readLine()) != null) {
            while (ligne.charAt(0) != '1') {
                ligne = in.readLine();//browse until line 1 is found
            }
            tuples = ligne.split(" ");
            itemset.add(tuples);
            System.out.println(Arrays.toString(itemset.get(0)));
            for (i = 2; i < TuplesCount(); i++) {
                ligne = in.readLine();
                tuples = ligne.split(" ");// THIS LINE THROWS THE EXCEPTION
                itemset.add(tuples);
                System.out.println(Arrays.toString(itemset.get(i)));
            }
        }
    } catch (IOException es) {
        es.printStackTrace();
    } catch (ArrayIndexOutOfBoundsException exepti) {
        exepti.printStackTrace();
    }
    return itemset;
}
  • 1
    You should let your IDE indent/format your code for you to make it easier to read and see scope of code blocks. – Pshemo May 02 '15 at 22:01
  • To format code `Ctrl+shift+f` in eclipse. – MChaker May 02 '15 at 22:04
  • 3
    NPE are very easy to catch: just start your program in debug mode, use your IDE static search to find where the variable ligne is written to. Then set breakpoints and fish the error – Raffaele May 02 '15 at 22:04
  • 1
    `readLine()` returns null at end of stream. You aren't testing for that anywhere, so you are inevitably going to incur these exceptions. It's the first thing you must do after calling `readLine(),` every time. – user207421 May 03 '15 at 08:06

3 Answers3

1

The code you provide us is really unreadable and should be formatted to easy debug it. Instead, you can try this simple code that i have tested on my IDE

package example;

import java.io.BufferedReader;
import java.io.FileReader;
import java.util.ArrayList;

public class FileSplit {

    public static void main(String[] args) {
        ArrayList<String[]> phrases = new ArrayList<String[]>();
        try{
            BufferedReader in = new BufferedReader(new FileReader("Department.txt"));
            String s;

            while((s = in.readLine()) != null){

                String[] words = s.split(" ");
                phrases.add(words);
            }

        }catch(Exception e){
            e.printStackTrace();
        }

        for(int i=0;i<phrases.size();i++){
            for(int j=0;j<phrases.get(i).length;j++)
            System.out.println(phrases.get(i)[j]);
        }
    }

}
MChaker
  • 2,610
  • 2
  • 22
  • 38
1

A NullpointerException tells you that your code

attempts to use null in a case where an object is required. These include:

  • Calling the instance method of a null object. ...

In your case, you've told us that the error occurs on

tuples = ligne.split(" ");

You're trying to call split on ligne and - given the documentation quote above - that implies that ligne is null at that point.

It's worth noting that it is the second occurence of that line that throws the Exception, so it is not as simple as the file not having a line that starts with 1

Why?

You need to use a debugger or use lots of System.out.println to convince yourself how the value of ligne changes as your code executes and, crucially, where it becomes null.

In your case - we don't know what TuplesCount() returns, but the likelihood is that you keep iterating in that loop beyond the end of the file, so the line immediately before the one that fails

ligne = in.readline();

can return null and you never check for that at that point. Note that conditions for the loops are only checked after each iteration of the loop - so , except for the one right at the top in the condition of the while loop, all the calls to ligne = in.readline(); could return null and are never checked.

Community
  • 1
  • 1
J Richard Snape
  • 20,116
  • 5
  • 51
  • 79
  • Thanks a lot for responding, TuplesCount returns the number of lines to be read minus the first two lines who aren't tuples (rows of a database) but metadata. – Meriem Larbi May 03 '15 at 07:36
  • For some reason, TuplesCount() was the problem :/ even though it returned the correct number of lines, it just didnt work so instead I made the return value of TuplesCount a parameter to the ExtractFile method and it worked: ExtractFile(TuplesCount()); – Meriem Larbi May 03 '15 at 08:08
  • @meriemlarbi Ok, glad to help. Please accept the answer if it solved the issue. See also the comment of EJP on your question re null checking, that's excellent advice. With regard to formatting code when posting- a good way is to paste in from eclipse, select the pasted block and press Ctrl-k to indent all equally. Good luck! – J Richard Snape May 03 '15 at 08:18
  • Just did, thanks again for helping me ^^ – Meriem Larbi May 05 '15 at 20:49
0

Are you testing this with a file which doesn't contain a line 1? If so, you run this it will keep executing the inner loop despite the fact that the value is null, resulting in an exception the time after the last line has been read. To fix this change the inner loop to be an if.

Like so:

public ArrayList ExtractionFile() {
    try {
        int i = 1;
        in = new BufferedReader(new FileReader(file));
        ligne = in.readLine(); //It can be more readable to seperate the assignment and the condtion
        while (ligne != null) {
            if (ligne.charAt(0) != '1') {
                ligne = in.readLine();//browse until line 1 is found
            } else {
                tuples = ligne.split(" ");
                itemset.add(tuples);
                System.out.println(Arrays.toString(itemset.get(0)));
                for (i = 2; i < TuplesCount(); i++) {
                    ligne = in.readLine();
                    tuples = ligne.split(" ");// CETTE LIGNE SOULEVE L EXCEPTION
                    itemset.add(tuples);
                    System.out.println(Arrays.toString(itemset.get(i)));
                }
            }
        }
    } catch (IOException es) {
        es.printStackTrace();
    } catch (ArrayIndexOutOfBoundsException exepti) {
        exepti.printStackTrace();
    }
    return itemset;
}

private int TuplesCount() {
    return Arrays.asList(tuples).size();
}

public static void main(String[] args){
    Main main = new Main();
    main.ExtractionFile();
}

}

As per some of the points above, please do format your code - it makes it easier to get help! Also, read up on breakpoints!

saml
  • 794
  • 1
  • 9
  • 20
  • Thanks a lot for responding :) . For the format, my code was formatted, since I wrote it on eclipse but I had to indent it to post it here, it's the first time I post a code here, I guess I didnt do it right... – Meriem Larbi May 03 '15 at 07:11