Failing to write multiple lines in a text files java loop

Tags:



I am trying to write many lines read from a file to a second file. I am able to loop through lines (sout can print all lines) of text but it’s not possible to write all lines in the new file. It writes only the last line.

Any help:

 lines.forEach(line -> {
                // Append the line separator
                String lineToWrite = line; // + System.lineSeparator(); //


                // Write every line to the output file
                try {
                    //Files.write(output, lineToWrite.getBytes(StandardCharsets.UTF_8));
                    //Files.write(output, Collections.singleton(lineToWrite),StandardCharsets.UTF_8);

                    PrintWriter writer = new PrintWriter(outputdir, "UTF-8");
                    writer.println(lineToWrite);
                    System.out.println(lineToWrite);
                    writer.close();


                } catch (IOException e) {
                    e.printStackTrace();
                    System.out.println("error lines linewrite:"+e);
                }
            });

Answer

You’re opening the file for reading, writing one line, and then closing it, for every line? That is incredibly inefficient.

Also, writing causes (checked) exceptions, and exceptions + lambdas don’t work well.

.forEach here is silly; the problem with lambdas are that they are not exception transparent, not mutable local variable transparent, and not control flow transparent. These are bad things. The use of the lambda needs to have enough positives to outweigh these negatives, OR the lambda needs to be separated in context (at which point those 3 downsides turn into upsides). Neither is the case here, so don’t use this old shoe to fasten than nail, use a hammer. Thus:

public static void main(String[] args) throws Exception {
    List<String> lines = ...;
    String file = "example.txt";

    try (PrintWriter out = new PrintWriter(file, "UTF-8")) {
        for (String line : lines) {
            out.println(line);
            System.out.println(line);
        }
    }
}

The above also fixes other errors in your code, such as not properly closing the resource, and deplorable exception management, by letting the system handler print the error, which does a better job generally. If somehow you can’t, the ‘best’ “I don’t know what to do with this” handler is not what you wrote, but this:

catch (IOException iCantHandleThis) {
    throw new RuntimeException("Uncaught", iCantHandleThis);
}

– but prefer throwing the exception onwards as is done in the example above.



Source: stackoverflow