12

What is the most preferred and concise way to print all the lines in a file using the new Java 8?

The output must be a copy of the file, line for line as in:

[Line 1 ...]
[Line 2 ...]

The question pertains to Java-8 with lambdas even though there are ways of doing it in older versions. Show what Java-8 is all about!

The Coordinator
  • 13,007
  • 11
  • 44
  • 73
  • Because the task is being done within a Java program. Obviously, if you are in MS-DOS or BASH, cat file works. But you knew that :) – The Coordinator Oct 29 '13 at 02:51

3 Answers3

28

This uses the new Stream with a lambda in a try enclosure.

I would say it is the most preferred and concise way because:

1) It will automatically close the stream when done and properly throw any exceptions.

2) The output of this is lazy. Each line is read after the last line is processed. This is also is closer to the original Java streams based file handling spec.

3) It prints each line in a manner that most closely resembles the data in the file.

4) This is less memory intensive because it does not create an intermediate List or Array such as the Files.readAllLines(...)

5) This is the most flexible, since the Stream object provided has many other uses and functions for working with the data (transforms, collections, predicates, etc.)

 try (Stream<String> stream = Files.lines(Paths.get("sample.txt"),Charset.defaultCharset())) {
            stream.forEach(System.out::println);
 }

If the path and charset are provided and the Consumer can take any Object then this works too:

 try (Stream stream = Files.lines(path,charset)) {
            stream.forEach(System.out::println);
 }

With error handling:

 try (Stream<String> stream = Files.lines(Paths.get("sample.txt"),Charset.defaultCharset())) {
            stream.forEach(System.out::println);
 } catch (IOException ex) {
        // do something with exception
 } 
The Coordinator
  • 13,007
  • 11
  • 44
  • 73
  • 1
    `CloseableStream` has been removed from recent versions of Java 8. All Streams are `AutoCloseable` though, so they can still be used with the try-with-resources construct. You just have to know which streams really need to be closed. – Stuart Marks Oct 26 '13 at 17:01
  • Thanks for the information. I have changed to just use Stream. – The Coordinator Oct 26 '13 at 18:06
11

You don't really need Java 8:

System.out.println(Files.readAllLines(path, charset));

If you really want to use a stream or need a cleaner presentation:

Files.readAllLines(path, charset).forEach(System.out::println);
assylias
  • 321,522
  • 82
  • 660
  • 783
  • 1
    Sure, those work. Thanks for showing some alternate ways. However, the question is for the best way using Java 8 -- not is Java 8 required. Now, your answer reads all the lines first and the Java 8 method is lazy and therefor more memory safe. Further, using Files.readAllLines(..) returns an Array or List and printing it is ugly and not the same as printing the file line by line. So, to keep with the most preferred and traditional behaviour of reading a file, line by line, and printing it, the Java 8 method looks best. – The Coordinator Oct 26 '13 at 10:04
  • 4
    The second code snippet addresses the ugly printing issue. As for laziness, it depends on your use case - if the file is not too large it is not really required. YMMV. – assylias Oct 26 '13 at 10:41
  • Very true and if I wasn't so anal, I would say your second method is the easiest to code. I really like the new Streams API and it has a few handy features which Java 8 offers. So I suppose it is a close tie :) – The Coordinator Oct 26 '13 at 10:42
5

Here is a simple solution:

System.out.println( new String(Files.readAllBytes(Paths.get("sample.java"))) );
Nery Jr
  • 3,849
  • 1
  • 26
  • 24
  • This solution with Nio 2 using the Files class and the readAllBytes method was not provided in any previous response !!! There's been a mistake in your comment, gknicker !! – Nery Jr Jan 30 '15 at 01:07
  • `readAllLines` is not `readAllFiles`, and `new String()` can also take a `Charset` argument. – David Moles May 06 '16 at 23:03