Solved

Writing to a file more efficently.

Posted on 1998-06-02
7
193 Views
Last Modified: 2010-03-04
Hi,
    I'm writing to a file but find the method I'm using is in-efficent.  What I do is read in a file, store it in a array, modify the corressponding array element to the line number and then print everything back to the file.  Is there a simplier way to just write a single line to a file?  So if I wanted to just write line 2 over in a 5 line file, I wouldn't have to touch any other lines.

Thanks in Advance.
0
Comment
Question by:cide
7 Comments
 
LVL 84

Expert Comment

by:ozo
ID: 1207038
perl -i.old -pe '$_ = "new line 2\n" if $.==2' file
0
 

Author Comment

by:cide
ID: 1207039
So do I actually use this line in the perl script?
0
 

Expert Comment

by:rkulper
ID: 1207040
Since the -i option rewrites the entire file anyway, I do not think it is any more efficient than what your currently doing. See perldoc perlrun -i option.

You could use the tell and seek functions, but this only works efficiently if all the line lengths are equal. If the line lengths are not equal, the only optimization I can think of is to use tell and seek to avoid changing the first unused part of the file.

Here is an example program that sorts the file "passwd" (assuming passwd contains lines of equal length).

#!/usr/local/bin/perl
$index=1; $position[0]=0;
unless (open FILE, "+<passwd") {
            print STDERR "Unable to open file: $!\n";
            exit;
}
while (<FILE>) {
      $array[$index]=$_;
      $position[$index]=tell FILE;
      $index++;
}
@sorted=sort @array;
$index=0;
while ($index <= $#array) {
      if($array[$index] ne $sorted[$index]) {
            seek FILE, $position[$index], 0;
            print FILE $sorted[$index];
      }
      $index++;
}
close FILE;
0
Is Your Active Directory as Secure as You Think?

More than 75% of all records are compromised because of the loss or theft of a privileged credential. Experts have been exploring Active Directory infrastructure to identify key threats and establish best practices for keeping data safe. Attend this month’s webinar to learn more.

 
LVL 84

Expert Comment

by:ozo
ID: 1207041
It is more efficient in that it does not store the entire file in n array.  see
perldoc perlfaq5

("passwd" may be a poor example of a file assumed to contain lines of equal length)
Also, starting at $index = 1 may make the ne between @lines and @sorted work differently than you intended.
I'd have just used push and shift, and not bother with $index at all.
0
 

Author Comment

by:cide
ID: 1207042
What is this -i option everyone is talking about?
0
 
LVL 84

Expert Comment

by:ozo
ID: 1207043
see
perldoc perlrun
Within a script, you could also use

{local $^I=".old"; local @ARGV=("file.name");
while( <> ){
  $_ = "new line 2\n" if 2..2;
  print;
}
}

0
 
LVL 2

Accepted Solution

by:
tpryor earned 50 total points
ID: 1207044
i would suggest using the "tie" keyword in perl 5.  You can tie a hash or an array to a text file.  When you write to the array/hash it writes to that line in the text file.

for example if you use TieFile.pm you could say...

tie @lines, TieFile', 'foo.txt';
print $lines[20];

When asked to fetch the nth line the TieFile module reads the file until it reaches that line and returns it.  Since it is wasteful to keep traversing the entire file every time a line is requested, TieFile keeps track of the file offsets of the beginning of each line so that when you ask it for a line that it has already visited, it knows the precise offset to seek before reading.

so the file is not stored in an array in memory and you can deal with the file on a specific line by line basis.

is this  what your looking for?

let me know I'll paste the TileFile.pm here.

GL
t
0

Featured Post

Is Your Active Directory as Secure as You Think?

More than 75% of all records are compromised because of the loss or theft of a privileged credential. Experts have been exploring Active Directory infrastructure to identify key threats and establish best practices for keeping data safe. Attend this month’s webinar to learn more.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

Title # Comments Views Activity
perl script to check whether folder contains any files 5 77
grep that displays 4 lines above & 1 line below of what's found 10 78
syslog unix file 20 68
Perl string filter 5 72
I have been pestered over the years to produce and distribute regular data extracts, and often the request have explicitly requested the data be emailed as an Excel attachement; specifically Excel, as it appears: CSV files confuse (no Red or Green h…
Checking the Alert Log in AWS RDS Oracle can be a pain through their user interface.  I made a script to download the Alert Log, look for errors, and email me the trace files.  In this article I'll describe what I did and share my script.
Explain concepts important to validation of email addresses with regular expressions. Applies to most languages/tools that uses regular expressions. Consider email address RFCs: Look at HTML5 form input element (with type=email) regex pattern: T…
Need to grow your business through quality cloud solutions? With everything required to build a cloud platform and solution, you may feel like the distance between you and the cloud is quite long. Help is here. Spend some time learning about the Con…

914 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

16 Experts available now in Live!

Get 1:1 Help Now