in my current script i read a file into an array, and then shift through the array (instead of reading <LINE> like through the file)
i was wasting a bunch of lines doing repetive kinda
while (@output and not $output[0] =~ /pattern/)
{stuff}
if (not @output)
{print "oh crap we hit EOF";}
and various other seeks like that, so i wrote this little ditty:
#Usage: shift_until(\@list, $pattern);
#shift off lines until we find $pattern
#returns true if found, false if we hit
#eof
sub shift_until(@$)
{
my ($arrayref, $pattern) = @_;
while (@$arrayref and not $$arrayref[0] =~ /$pattern/)
{
shift @$arrayref;
}
(@$arrayref) ? return 1 : return 0;
}
pretty much every seek i do for this script, if i don't find what i was looking for, the whole thing is fscked, so slurping the whole file into the void is not a problem. otherwise i would used grep, or returned an array index or some such different junk. anyway this musta cut tons of lines outta my program, it made me happy.
------------------
"Assembly of Japanese bicycle require great peace of mind."
Registered Linux User #188285 http://counter.li.org/
commdogg
01-19-2001, 09:29 PM
How about this...
#!/usr/bin/perl
use strict;
use warnings;
open (FILE, "file");
my @file = <FILE>;
my $count = 1;
while (@file && !($file[0] =~ /yo/i)) {
print "$count: $file[0]";
$count++;
shift @file;
}
if (!($file[0] eq '')) {
print "Oh crap, EOF\n";
}
And in "file"...
Hello Dude
Hi
Yo!
I don't know your goal in the script, but this works for me. Just edit it appropriately, and there you go!
P.S. I hope this works, then I can say I helped one of the bigger contributors to the Programming Forum!
YaRness
01-20-2001, 06:53 PM
what my intent was with that new subroutine was to replace that while/if combo (where the WHILE loop would shift through until EOF or pattern match, and then the if would check for EOF) with just one if call, like
if ( not shift_until(@output, $pattern) )
{#there was an error}
just happens in my script that, if a pattern i am looking for is missing, then the whole file is fscked, so i want every other seek/check/thingy to not do anything either. so every other parsing doodad in my script includes some check for an empty array.
i wasn't askin for help with nothin, just sharing a snippet.. not sure if you misread something or what, but thanks for the gesture at any rate.
------------------
"Assembly of Japanese bicycle require great peace of mind."
Registered Linux User #188285 http://counter.li.org/
commdogg
01-21-2001, 05:12 PM
Oops, Sorry. http://www.linuxnewbie.org/ubb/redface.gif I'm so embarrased http://www.linuxnewbie.org/ubb/redface.gif
TheLinuxDuck
01-21-2001, 05:16 PM
Originally posted by commdogg:
Oops, Sorry. http://www.linuxnewbie.org/ubb/redface.gif I'm so embarrased http://www.linuxnewbie.org/ubb/redface.gif
Don't be!!! http://www.linuxnewbie.org/ubb/smile.gif Offering code and offering help to others is what this forum is about. I'm sure that YaR appreciated your effort.
------------------
TheLinuxDuck
I have a belly button.
:wq
TheLinuxDuck
01-22-2001, 02:03 AM
Originally posted by YaRness:
#Usage: shift_until(\@list, $pattern);
#shift off lines until we find $pattern
#returns true if found, false if we hit
#eof
So, you don't actually do anything with the information in the file, you just check to see whether it contains a certain piece of information?
So, why not just pass the filename into the sub instead of an array ref, and do all the file handling in the sub? That way, you could return true/false and not have any external variable declarations.
Or if the info from the file *is* needed, just return a reference to an array containing what was left in the file, instead of slurping the entire file into an array. Something like:
#!/usr/bin/perl -w
use strict;
sub shift_until($$);
sub shift_until($$)
{
my($filename,$pattern)=@_;
my($found,@buffer);
open MYFILE, $filename or return undef;
while(<MYFILE> ) {
$found=defined if(/$pattern/ && !$found);
push @buffer, $_ if($found);
}
close(MYFILE);
return undef unless(@buffer and return(\@buffer));
}
That would let you get away from slurping an entire file into an array just for a certain part of it.. The routine could lose all the @buffer business if you didn't actually need the data.
JMTCW.. http://www.linuxnewbie.org/ubb/wink.gif
------------------
TheLinuxDuck
I have a belly button.
:wq
[This message has been edited by TheLinuxDuck (edited 22 January 2001).]
YaRness
01-22-2001, 09:35 AM
TLD: i'm tired and sick, and at work (what a great combination), so i'm not understanding things clearly right now, and therefore only kinda skimmed your post. but lemme demonstrate what my file is is like, and what i do with it, so maybe things will be clearer (or, at the very least, no more murky than usual).
first of all, i want to minimize the time that the file is actually open, for various reasons. so i open it, dump it to an array, and then close it... THEN just work with the array.
now, being a log of sorts as my data in this case is (and usually is), there's a bunch of extraneous crap that i don't need. so my file looks something like this i guess
header junk
junk
junk
other junk
...
ad nauseum
*STUFF I NEED*
*STUFF I NEED*
*STUFF I NEED*
junk
junk
*DATA I NEED
...
...
...
END OF DATA I NEED*
junk to EOF
so, when i'm reading the array, i just kinda throw away lines until i get to SOMETHING I NEED, then i actually work with the data, or shift through a line at a time working with stuff, until i get to more junk, then i slurp through to the next relevant thing, shifting off lines into the void until i get to more relevant junk. actually, i really only look at two (three if there's an error) chunks of stuff, i seek to the first section, get some data, seek to the second section, slurp up some data, then shift off the last few lines until @output is empty, then i know i'm done parsing data, and i can finish examining it and print out my results.
so in conclusion, i use that shift_until function several times to slurp through the file array until i get to something useful. if i end up with an empty array instead of finding a key point to start reading information in, doesn't matter because it means something went horribly wrong, and the file is useless anyway (by horribly wrong, i mean on the caliber of the hard drive failed in the middle of a write operation, or something else fubared the file in the split second between generating it and parsing it).
now, all that being said, i just remembered i changed the way everything works a little. there IS no file being read anymore. what i was doing was doing a system() call to a propriertary script program, basically
system ("scriptprogram $script > $outputfile);
#parse $outputfile
but i skipped all that now and i'm doing
@output = `scriptprogram $script`;
#notice those are backticks
and skipping all that extraneous file stuff altogether. i think everything else i said applies and junk.
ok, now where's my dayquil.
------------------
"Assembly of Japanese bicycle require great peace of mind."
Registered Linux User #188285 http://counter.li.org/
TheLinuxDuck
01-22-2001, 10:47 AM
Originally posted by YaRness:
TLD: i'm tired and sick, and at work (what a great combination), so i'm not understanding things clearly right now
Hey dood, I'm sorry to hear you're under the weather.. I know how it is.. I recently got off of a 2 week illness than caused me to miss about 4 days of work. My paycheck this pay period reminded me of that.. : http://www.linuxnewbie.org/ubb/redface.gifuch::
The only thing I can suggest is lots of sleep, tylenol every 6 hours, and vitamin c twice a day. http://www.linuxnewbie.org/ubb/smile.gif
first of all, i want to minimize the time that the file is actually open, for various reasons. so i open it, dump it to an array, and then close it... THEN just work with the array.
I'm picking up what you're laying down.. http://www.linuxnewbie.org/ubb/smile.gif That makes sense.. of course, if access share problems are a concern, you could always lock the file before you start handling it, but hey, that's neither here nor there... http://www.linuxnewbie.org/ubb/smile.gif I understand the need for quick and fast file access..
and skipping all that extraneous file stuff altogether. i think everything else i said applies and junk.
ok, now where's my dayquil.
::grin:: That makes sense. And shifting the array into nothing makes sense, since you're not needing any of the info.
Dood, I truely hope that you begin to feel better. I know the thing that helped me the most was sleep. http://www.linuxnewbie.org/ubb/smile.gif
------------------
TheLinuxDuck
I have a belly button.
:wq
YaRness
01-22-2001, 11:01 AM
i may be over exaggerating illness. or more likely, i think it's being TIRED from being kinda blah yesterday, plus my throat is still scratchy, that is makin me feel like i should be at home in bed today. but thinking on it, i've been at work when i was REALLY sick (fever and all that), and that is not quite what it is today. just kinda exhausted from a long, tediuous weekend, plus a little bit of leftover scratchiness in the throat region from post-nasal drippiness (which could have resulted from irritation from the dry air in the apt... got cold this weekend so stupid heat was on more)...
if access share problems
are a concern, you could always lock the file before you start handling it, but hey, that's neither
here nor there.
if that was a concern, then locking the file would be a wonderful notion. s'not though, this isn't even running on a network. it's more along the lines of not wanting to keep the data handy after we're done examining it (also not displaying any data to the terminal screen.. security stuff http://www.linuxnewbie.org/ubb/wink.gif ). i was so glad when i re-learned about using backtick type stuff, eliminated the scratch file altogether.
------------------
"Assembly of Japanese bicycle require great peace of mind."
Registered Linux User #188285 http://counter.li.org/
TheLinuxDuck
01-22-2001, 11:23 AM
Originally posted by YaRness:
i may be over exaggerating illness. or more likely, i think it's being TIRED from being kinda blah yesterday, plus my throat is still scratchy
Oh, so you're going for the sympathy edge, eh? http://www.linuxnewbie.org/ubb/smile.gif http://www.linuxnewbie.org/ubb/smile.gif J/k, I understand, I think I feel pretty much the same way (minus the throat scratchiness)
i was so glad when i re-learned about using backtick type stuff, eliminated the scratch file altogether.
One of the things that takshaka really stressed to me was "If you're going to use perl, use perl all the way". With that said.. http://www.linuxnewbie.org/ubb/biggrin.gif .. here's the backtick thing you're doing, but a little more perlish. http://www.linuxnewbie.org/ubb/smile.gif All I'm doing is opening up the program and piping the output through the filehandle. Very nice stuff. http://www.linuxnewbie.org/ubb/smile.gif
open(MYFILE, "| scriptname $script") or die "Couldn't pipe scriptname $script: $!\n";
my(@output)=<MYFILE>;
close(MYFILE);
I tried this with the old 'grades' perl script you were working on some time ago (which I still have btw). http://www.linuxnewbie.org/ubb/smile.gif
------------------
TheLinuxDuck
I have a belly button.
:wq
YaRness
01-22-2001, 11:54 AM
open(MYFILE, "| scriptname $script") or die "Couldn't pipe scriptname $script: $!\n";
my(@output)=<MYFILE>;
close(MYFILE);
[/b]
<HR></BLOCKQUOTE>
hmm. that might be a good idea. i already have a check WAY in the beginning of the program that just flat-out bails if the third-party script program isn't available ("(-e program) or die"), but that open/close bit might be good for when Something Goes Wrong™.
on another note, i've been, whadya call it, talking back and forth (well email) with the guy that maintains the perl .vim file (<EDIT> syntax file. there's a lot of vim stuff that ends in .vim :P ). a couple of things: he patched the .vim file for me so it will correctly highlight imbedded comments in s!!!x or m!!x type thingies, but ONLY if you use the "!" delimiter, and it won't work for !!x (the updated version is PROBABLY on his site, but i can email the one he sent to me if you want it). the other thing he clarified for me is that if you do
print <<EOF
yar
EOF
it will only correctly highlight it if you use "EOF", or a couple other specific markers (i think also ""EOF"", "", "''", """", or something in there. basically EOF or a blank thingy maybe). i had been doing "print <<ENDPRINT" in my handshake.. was having to stick that sub at the end so it didn't fubar the rest of the highlighting.
------------------
"Assembly of Japanese bicycle require great peace of mind."
Registered Linux User #188285 http://counter.li.org/
[This message has been edited by YaRness (edited 22 January 2001).]
justlinux.com
Copyright Internet.com Inc. All Rights Reserved.