Skip a line using BufferedReader (skip, but not read it)

4.3k views Asked by At

Hi guys I am currently using BufferedReader to read files. I have something like:

br.readLine() != null

for each call loop.

And now what should I do if I want to skip a line. Here, I've read several similar questions other people posted, most of them suggested using readLine().

I know calling readLine() once will cause the pointer to the next line. But this is not preferred as I am considering the reading performance here. Although you seem to skip a line, the system actually read it already, so it is not time-efficiency. What I want is to move the pointer to the next line, without reading it.

Any good idea?

5

There are 5 answers

0
Tagir Valeev On BEST ANSWER

If you care about the memory wasted in the intermediate StringBuffer, you can try the following implementation:

public static void skipLine(BufferedReader br) throws IOException {
    while(true) {
        int c = br.read();
        if(c == -1 || c == '\n')
            return;
        if(c == '\r') {
            br.mark(1);
            c = br.read();
            if(c != '\n')
                br.reset();
            return;
        }
    }
}

Seems that it works nicely for all the EOLs supported by readLine ('\n', '\r', '\r\n').

As an alternative you may extend the BufferedReader class adding this method as instance method inside it.

0
Karrde On

It's not possible to skip the line without reading it.

In order to know where to skip to, you have to know where the next new line character is, so you have to read it.

P.S. Unless you have a good reason not to, BufferedReader should be fine for you - it's quite efficient

0
m4ktub On

In general, it's not possible in any language and with any API.

To skip a line you need to know the next line's offset. Either you have a file format that provides you that information, you are given line offsets as input, or you need to read every single byte just to know when a line ends and the next begins.

0
StephaneM On

Have you read the code of readLine()? It reads chars one by one until it finds an \r or a \n and appends them to a StringBuffer. What you want is this behaviour without the burden of creating a StringBuffer. Just override the class BufferedReader and provide your own implementation which juste reads chars until /r or /n without building the useless String.

The only problem I see is that many fields are private...

0
Tirinoarim On

You'll sometimes have a problem skipping the first line with code analysis tools (sonar etc), complaining that you didn't use the value. In the case of CSV, you may want to skip (i.e. not use) the first row if its headers. In which case, you could stream the lines and skip perhaps?

try (BufferedReader reader = new BufferedReader(new FileReader(filename))) {
  Stream<String> lines = reader.lines().skip(1);

  lines.forEachOrdered(line -> {

  ...
  });
}