Java-esque way of doing this.

P

Prabh

Hello all,
I'm rather new to Java and was wondering if there is a more Java-esque
way of doing the following.
I need to update a particular line of a file, foo.txt keeping all the
other lines exactly the same.

I am thinking of :
1) Copy foo.txt to foo.txt.bak.
2) Use FileReader and LineNumberReader to read each line in the .bak.
3) Use PrintWriter, pw.print to print each of the above line to the
original.
a) With no changes, if line doesnt match the required pattern.
b) With changes, if line matches the pattern.

I realize this is a clunky-shell scripting way of doing things.
Is there a more Java-esque way of doing this?

Could I bypass the "backup the original file" part?
Is there a way I can read and write the same file?
Read the original file in some temp stream, process stream
line-by-line, write /w or w/o changes to the same file.

What Input/Output streams should I be looking at?

Thanks,
Prabh
 
R

Roedy Green

I realize this is a clunky-shell scripting way of doing things.
Is there a more Java-esque way of doing this?

if the line is precisely the same length, you can plop the new stuff
on top with random access . See http://mindprod.com/fileio.html for
sample code.

If the file is of reasonable size, read the whole thing in one great
gulp into a String. See http://mindprod.com/fileio.html for sample
code. Then manipulate that giant string to the new desired image and
write it out again in one great gulp, or perhaps three little ones.
 
M

Matt Humphrey

Prabh said:
Hello all,
I'm rather new to Java and was wondering if there is a more Java-esque
way of doing the following.
I need to update a particular line of a file, foo.txt keeping all the
other lines exactly the same.

I am thinking of :
1) Copy foo.txt to foo.txt.bak.
2) Use FileReader and LineNumberReader to read each line in the .bak.
3) Use PrintWriter, pw.print to print each of the above line to the
original.
a) With no changes, if line doesnt match the required pattern.
b) With changes, if line matches the pattern.

I realize this is a clunky-shell scripting way of doing things.
Is there a more Java-esque way of doing this?

Could I bypass the "backup the original file" part?
Is there a way I can read and write the same file?
Read the original file in some temp stream, process stream
line-by-line, write /w or w/o changes to the same file.

What Input/Output streams should I be looking at?

Thanks,
Prabh

The key problem that you're facing is that text files are contiguous
sequences of characters and it is only possible to simply replace one line
with a different line when it is exactly the same size. Because the
replacement line may be larger (or smaller and add extra blanks or
something), you have to remake the file. I think the only exception to your
plan is that you should not copy the original but make the modified file as
foo.out. If the replacement is successful, rename foo.out as foo.txt.

Cheers,
Matt Humphrey (e-mail address removed) http://www.iviz.com/
 
C

Chris Uppal

Roedy said:
If the file is of reasonable size, read the whole thing in one great
gulp into a String. See http://mindprod.com/fileio.html for sample
code. Then manipulate that giant string to the new desired image and
write it out again in one great gulp, or perhaps three little ones.

Or read the file into a collection (a java.util.ArrayList, perhaps) of Strings,
one
for each line.

-- chris
 
A

antroy

I realize this is a clunky-shell scripting way of doing things.
Is there a more Java-esque way of doing this?

Could I bypass the "backup the original file" part?

The others have addressed your problem in more detail. This part might
be an interesting sidenote however - you can use createTempFile(String
name, String suffix) to create a temporary file, and then deleteOnExit():

File temp = File.createTempFile("temp","bak");
temp.deleteOnExit();

Do whatever you need to with the temp file, and it will be automatically
removed from your filesystem when the program terminates (when the JVM
exits).
 
R

Roedy Green

Do whatever you need to with the temp file, and it will be automatically
removed from your filesystem when the program terminates (when the JVM
exits).

There is a problem with this. If your app crashes, then they won't be
deleted. If you have not given them some distinctive extension or
name, you can't very well run a file-deleting filter to find them
later and kill them.

So, I'd say in general, delete them right after you close them. That
does not eliminate the problem, but it reduces it.
 
H

Harald Hein

Roedy Green said:
There is a problem with this. If your app crashes, then they
won't be deleted.

This depends on the operating system. It is trivial to get this working
under Unix.
 
R

Roedy Green

This depends on the operating system. It is trivial to get this working
under Unix.

what I do is use a .tmp extension on my temps, and then run Batik each
day which scans my disk for .top files and kills them. It also
totally empties various caches. The problem is you have to customise
the list of directories to scan for every machine.
 
H

Harald Hein

Roedy Green said:
What's the trick on Unix to ensuring temp files get deleted?

If we ignore Java for a moment you do the following: You open a file,
you get and keep a file handle, but you immediately unlink (remove) the
file. Due to the unlink it is gone from the directory. Due to Unix's
way of handling files, the file handle is still vaid, the file still
exists (it just doesn't have a directory handle) and the process
holding the file handle can read and write to it at will.

Unix keeps the file until a process has an open handle to it. When you
exit the process or the process crashes, the file gets closed. Since it
has no directory entry, Unix removes the file at that point.

That's the good news. The bad news is you have to be very lucky to get
this behaviour in Java because of the thick layer Java-IO has wrapped
around the necessary Unix system calls.
 
S

Steve Bowman

In a multi-threaded world:

I generally have a cleanup task present in most of my applications. It
is simply spawned off as a separate thread and watches over what
everything else is doing. It generally cleans up after other threads
collapse for what ever reason. When handling files, Java tends to
screw up occasionally, so the clean-up step is quite important.

The suggestion way back of having a new file created and then moving
it in to the correct place is good. This way other applications won't
complain when they see an incomplete/wierd file.

My 2 cents.
 
M

Mike Baranczak

Roedy Green said:
There is a problem with this. If your app crashes, then they won't be
deleted.


Incorrect. If your app crashes due to an uncaught exception, the JVM
will still clean up your temp files. (That's the way it works with
Apple's latest JRE; I'd assume that others work the same, but I could be
wrong.)

If the JVM itself crashes, then that's different; but crashing the JVM
is usually pretty damn difficult, unless you're working with buggy JNI
code.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,764
Messages
2,569,564
Members
45,039
Latest member
CasimiraVa

Latest Threads

Top