How to create and write a .Txt file in Java? [duplicate] - java

This question already has an answer here:
Java PrintWriter not working
(1 answer)
Closed 6 years ago.
import java.io.BufferedReader;
import java.io.File;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
public class FileGenerator {
/**
* #param args
*/
public static void main(String[] args) {
File outputFile;
BufferedReader reader;
FileWriter fileWriter;
try {
outputFile = new File("test.txt");
outputFile.createNewFile();
fileWriter = new FileWriter(outputFile, false);
reader = new BufferedReader(new FileReader("template.txt"));
StringBuilder sb = new StringBuilder();
String line = reader.readLine();
while (line != null) {
sb.append(line);
sb.append(System.lineSeparator());
line = reader.readLine();
}
String everything = sb.toString();
fileWriter.write(everything);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
}
}
}
The fileWriter creates test.txt but the string inside of test.txt is empty. i want it doesnt happen empty. by the way you may say "String everything" can be empty. But it isnt. When i try without reader txt i mean "String everything = "some text", it happens same. it happens empty

The file is empty because the contents of everything are smaller than the operating systems and / or Java's I/O buffers, and the program ends without properly closing the file.
When you write something to a file, and you need to ensure that it is written without closing the file already, call flush().
Whenever you open an I/O resource, close it using close() after use. close() implies flushing the buffers.
Java 7 provides try-with-resources for that, like this:
try (FileWriter writer = new FileWriter("foo.txt")) {
writer.write("Hello, world!\n");
writer.flush();
// do more stuff with writer
} // <- closes writer implicitly as part of the try-with-resources feature

As suggested in the comments, you need to do fileWriter.close() in order to close the output stream. If it is a buffered writer, then closing it not necessary as explained here.
Is it necessary to close a FileWriter, provided it is written through a BufferedWriter?

Related

How to use a regular expression to parse a text file and write the result on another file in Java

I used a regular expression to parse a text file to use the resulted group one and two as follows:
write group two in another file
make its name to be group one
Unfortunately, No data is written on the file!
I did not figure out where is the problem, here is my code:
package javaapplication5;
import java.io.*;
import java.util.regex.*;
public class JavaApplication5 {
public static void main(String[] args) {
// TODO code application logic here
try {
FileInputStream fstream = new FileInputStream("C:/Users/Welcome/Desktop/End-End-Delay.txt");
DataInputStream in = new DataInputStream(fstream);
BufferedReader br = new BufferedReader(new InputStreamReader(in));
File newFile1= new File("C:/Users/Welcome/Desktop/AUV1.txt");
FileOutputStream fos1= new FileOutputStream(newFile1);
BufferedWriter bw1= new BufferedWriter(new OutputStreamWriter(fos1));
String strLine;
while ((strLine = br.readLine()) != null) {
Pattern p = Pattern.compile("sender\\sid:\\s(\\d+).*?End-End\\sDelay:(\\d+(?:\\.\\d+)?)");
Matcher m = p.matcher(strLine);
while (m.find()) {
String b = m.group(1);
String c = m.group(2);
int i = Integer.valueOf(b);
if(i==0){
System.out.println(b);
bw1.write(c);
bw1.newLine();
}
System.out.println(b);
// System.out.println(c);
}
}
}
catch (Exception e) {
System.err.println("Error: " + e.getMessage());
}
}
}
Can anyone here help me to solve this problem and Identify it?
You are using BufferedWriter, and never flush (flushing writer pushes the contents on disk) your writer or even close it at the end of your program.
Due to which, before your content gets written in actual file on disk from BufferedWriter, the program exits and the contents get lost.
To avoid this, either you can call flush just after writing contents in bw1,
bw1.write(c);
bw1.newLine();
bw1.flush();
OR
Before your program ends, you should call,
bw1.close(); // this ensures all content in buffered writer gets push to disk before jvm exists
Calling flush every time you write the data is not really recommended, as it defeats the purpose of buffered writing.
So best is to close the buffered writer object. You can do it in two ways,
Try-with-resources
Manually close the buffered writer object in the end, likely in the finally block so as to ensure it gets called.
Besides all this, you need to ensure that your regex matches and your condition,
if(i==0){
gets executed else code that is writing data in file won't get executed and of course in that case no write will happen in file.
Also, it is strongly recommended to close any of the resources you open like file resources, database (Connection, Statements, ResultSets) resources etc.
Hope that helps.

Java: FileReader and FileWriter not working together

So, I'm trying to make a program that can write and then read the exact same text file using only FileWriter and FileReader, but for some reason, when I put both of these classes at the same code, FileWriter works properly, but FileReader does not, and I get an empty output.
import java.io.*;
import java.util.Scanner;
public class ex2 {
public static void main(String[] args) {
File file = new File("C:\\a.txt");
Scanner scanner = new Scanner(System.in);
try {
FileReader reader = new FileReader(file);
FileWriter writer = new FileWriter(file);
writer.write(scanner.nextLine());
int ch;
while ((ch = reader.read()) != -1) {
System.out.println((char)ch);
}
scanner.close();
reader.close();
writer.close();
} catch (Exception e) {
}
}
}
That's the code I'm talking about. I can write anything to a.txt, but reader does not seem to be able to read a thing. The weird part is, if I use the exact same code but without the file writing parts, FileReader works normally as it should. What am I doing wrong? Thanks in advance!
FileWriter objects are buffered. That means they won't write everything you give them as soon as you call write. They'll wait until they have a certain amount to write and then write it all at once. Just add this line:
writer.flush();
between your writing and your reading.

java filewriter write incomplete data of instance

i had a input file having 45311 instance. after applying my programing task. when i m write it back in new file it actually write 43371 instance only.it is run successfully but where are my remaining instances.
package kmean;
//package greenblocks.statistics;
import java.io.IOException;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.FileWriter;
import weka.clusterers.SimpleKMeans;
import weka.core.Instances;
/**
*
* #author admin
*/
public class Kmean {
public static BufferedReader readDataFile(String filename) {
BufferedReader inputReader = null;
try {
inputReader = new BufferedReader(new FileReader(filename));
} catch (FileNotFoundException ex) {
System.err.println("File not found: " + filename);
}
return inputReader;
}
/**
* #param args the command line arguments
*/
public static void main(String[] args) throws IOException, Exception {
BufferedWriter writer = null;
try {
writer = new BufferedWriter(new FileWriter("perturbed1.csv"));
}
catch (IOException e) {
}
SimpleKMeans kmeans = new SimpleKMeans();
kmeans.setSeed(10);
//important parameter to set: preserver order, number of cluster.
kmeans.setPreserveInstancesOrder(true);
kmeans.setNumClusters(5);
BufferedReader datafile = readDataFile("elecNormNew.arff");
// BufferedReader datafile = readDataFile("perturbed.csv");
Instances data = new Instances(datafile);
kmeans.buildClusterer(data);
// This array returns the cluster number (starting with 0) for each instance
// The array has as many elements as the number of instances
int[] assignments = kmeans.getAssignments();
StringBuilder sb = new StringBuilder();
int i=0;
for(int clusterNum : assignments) {
// System.out.printf("Instance %d -> Cluster %d \n", i, clusterNum);
sb.append(i);
sb.append(";");
sb.append(clusterNum);
sb.append("\n");
//System.out.printf("\n");
i++;
}
System.out.println(sb.toString());
writer.write(sb.toString()+"\n");
// TODO code application logic here
}
}
The neat fact about buffered file writers are, that they take your input and keep it, until the buffer is full. This reduces the i/o operations. At best one write operation fits into one hdd write buffer so the operating system take the whole buffer as one i/o command. The downside is that if at the end if you do not flush() the buffer, the rest of the content will not be written to disk. If you call close() any pending bytes will be written and the resources be freed. In java 7 and above you can use the autoclosing feature by just opening the stream in your try statement:
try(Inputstream is = new ...) {
If you may have any data to write after your code, you can use .flush() to ensure the data is written.
The buffer size is set by default to 8k, but this may wary from jre and version.
You should call writer.close() at the end after writing all data.
insted of writer.write(sb.toString()+"\n");
try writer.write(sb.toString()+writer.newLine());
and finish your writig progress with a
writer.flush();
writer.close();
had some problems myself with "\n" maby thats the problem.

Merge huge files without loading whole file into memory?

I want to merge huge files containing strings into one file and tried to use nio2. I do not want to load the whole file into memory, so I tried it with BufferedReader:
public void mergeFiles(filesToBeMerged) throws IOException{
Path mergedFile = Paths.get("mergedFile");
Files.createFile(mergedFile);
List<Path> _filesToBeMerged = filesToBeMerged;
try (BufferedWriter writer = Files.newBufferedWriter(mergedFile,StandardOpenOption.APPEND)) {
for (Path file : _filesToBeMerged) {
// this does not work as write()-method does not accept a BufferedReader
writer.append(Files.newBufferedReader(file));
}
} catch (IOException e) {
System.err.println(e);
}
}
I tried it with this, this works, hower, the format of the strings (e.g. new lines, etc is not copied to the merged file):
...
try (BufferedWriter writer = Files.newBufferedWriter(mergedFile,StandardOpenOption.APPEND)) {
for (Path file : _filesToBeMerged) {
// writer.write(Files.newBufferedReader(file));
String line = null;
BufferedReader reader = Files.newBufferedReader(file);
while ((line = reader.readLine()) != null) {
writer.append(line);
writer.append(System.lineSeparator());
}
reader.close();
}
} catch (IOException e) {
System.err.println(e);
}
...
How can I merge huge Files with NIO2 without loading the whole file into memory?
If you want to merge two or more files efficiently you should ask yourself, why on earth are you using char based Reader and Writer to perform that task.
By using these classes you are performing a conversion of the file’s bytes to characters from the system’s default encoding to unicode and back from unicode to the system’s default encoding. This means the program has to perform two data conversion on the entire files.
And, by the way, BufferedReader and BufferedWriter are by no means NIO2 artifacts. These classes exists since the very first version of Java.
When you are using byte-wise copying via real NIO functions, the files can be transferred without being touched by the Java application, in the best case the transfer will be performed directly in the file system’s buffer:
import static java.nio.file.StandardOpenOption.*;
import java.io.IOException;
import java.nio.channels.FileChannel;
import java.nio.file.Path;
import java.nio.file.Paths;
public class MergeFiles
{
public static void main(String[] arg) throws IOException {
if(arg.length<2) {
System.err.println("Syntax: infiles... outfile");
System.exit(1);
}
Path outFile=Paths.get(arg[arg.length-1]);
System.out.println("TO "+outFile);
try(FileChannel out=FileChannel.open(outFile, CREATE, WRITE)) {
for(int ix=0, n=arg.length-1; ix<n; ix++) {
Path inFile=Paths.get(arg[ix]);
System.out.println(inFile+"...");
try(FileChannel in=FileChannel.open(inFile, READ)) {
for(long p=0, l=in.size(); p<l; )
p+=in.transferTo(p, l-p, out);
}
}
}
System.out.println("DONE.");
}
}
With
Files.newBufferedReader(file).readLine()
you create a new Buffer everytime and it gets always reset in the first line.
Replace with
BufferedReader reader = Files.newBufferedReader(file);
while ((line = reader.readLine()) != null) {
writer.write(line);
}
and .close() the reader when done.
readLine() does not yield the line ending ("\n" or "\r\n"). That was the error.
while ((line = reader.readLine()) != null) {
writer.write(line);
writer.write("\r\n"); // Windows
}
You might also disregard this filtering of (possibly different) line endings, and use
try (OutputStream out = new FileOutputStream(file);
for (Path source : filesToBeMerged) {
Files.copy(path, out);
out.write("\r\n".getBytes(StandardCharsets.US_ASCII));
}
}
This writes a newline explicitly, in the case that the last line does not end with a line break.
There might still be a problem with the optional, ugly Unicode BOM character to mark the text as UTF-8/UTF-16LE/UTF-16BE at the beginning of the file.

File I/O producing gibberish on output

I'm learning File I/O using Java.
Following are my codes from two different Java files. One is "File" with the main class, the other is "FileWrite."
I was able to implement string input and output. But the output textfile has gibberish in the beginning and I am not sure why.
[File.Java]
package file;
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
public class File {
public static void main(String[] args) {
try (BufferedReader br = new BufferedReader(new FileReader("B:\\fileIn.txt")))
{
String stCurrent;
while ((stCurrent = br.readLine()) != null) {
System.out.println(stCurrent);
}
} catch (IOException e) {
e.printStackTrace();
}
FileWrite fW = new FileWrite();
fW.serializeAddress("Boston", "Canada");
}
}
[FileWrite.Java]
package file;
import java.io.FileOutputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
public class FileWrite {
public void serializeAddress(String city, String country) {
try {
FileOutputStream fout = new FileOutputStream("B:\\address.txt");
ObjectOutputStream obOut = new ObjectOutputStream(fout);
obOut.writeUTF(city);
obOut.writeUTF(country);
obOut.close();
System.out.println("Output Done");
} catch(Exception ex) {
ex.printStackTrace();
}
}
}
Now, on "obOut.writeUTF(city); obOut.writeUTF(country);" I separated out two string inputs. Is there a way to combine them into one? As in obOut.writeUTF(city, counry) instead of two. Or is this only achievable through making these into an object?
[Update]
Imported a couple more and I tried
PrintStream ps = new PrintStream(new FileWriter("B:\\addressPS.txt"));
ps.println(city);
ps.println(country);
ps.close();
But with errors, any clue?
You are doing the right thing keeping them separate already. City and country are different fields.
A very common mistake is not making a distinction between binary and text files/socket streams. You are a mixing the two which will lead to confusion. I suggest you only sue text Writer/Reader or binary Input/OuptutStream unless you have a very clear idea of what you are doing.
In short if you what to write text use
PrintStream ps = new PrintStream(new FileWriter(textFileName));
ps.println(city);
ps.println(country);
ps.close();
writeUTF takes strings also, you don't have to create new object for city and county.
Cant you do obOut.writeUTF(city +" "+country); ?
The gibberish is because .writUTF() writes data in a modified UTF format which is mentioned in the javadocs.
An ObjectOutputStream is generally used to output OBJECTS but I suppose you can use it for strings as well. You can use the respective .readUTF() method in the ObjectInputStream class in order to read the data in your file back.
Also, you have tried to use the try-with-resources block which is new to Java SE7. You should NOT do it the way you have done so. You should do this instead:
try (FileReader fr = new FileReader("B:\\fileIn.txt"); BufferedReader br = new BufferedReader(fr);) {
} catch (FileNotFoundException e1) {
e1.printStackTrace();
} catch (IOException e1) {
e1.printStackTrace();
}
Splitting the FileReader and the BufferedReader will allow Java SE7 to close both the streams with ease. The way you have done it, only the BufferedReader stream will get closed after the try block finishes.
By definition, ObjectOutputStream produces 'gibberish'. It's not intended for human consumption, it is a format used to write out objects so that you can read them back. You're not supposed to be able to make sense of the results in a text editor. To make human-readable content, just use an OutputStreamWriter or even a PrintWriter. In short, your last example is correct, and if you get errors, please edit your question to tell us what the errors are.

Categories

Resources