in reply to Re: Reading two text files parallelly...
in thread Reading two text files parallelly...

I'm new to Perl as well, and all of the examples that I've come across instruct you to open a file like this:

open (FH, "<$file1") or die "blahblah";

Would you (or anyone for that matter) mind elaborating as to why 1) and 2) should be used?

Much appreciated in advance.

Replies are listed 'Best First'.
Re^3: Reading two text files parallelly...
by eyepopslikeamosquito (Archbishop) on Nov 09, 2010 at 12:01 UTC

    See the first four items of Perl Best Practices Chapter 10 (I/O), namely:

    • Don't use bareword filehandles
    • Use indirect filehandles
    • If you have to use a package filehandle, localize it first
    • Use either the IO::File module or the three-argument form of open

    Using lexical file handles is better style because:

    • They are local variables and so avoid the generally evil programming practice of keeping state in global variables.
    • They close themselves automatically when their lexical variable goes out of scope.
    • They avoid the confusion of barewords. IMHO, barewords are an unfortunate Perl feature. Admittedly, they're handy when writing poems or playing golf. Historically, they probably exist only because of the improbable chance circumstance of Larry sitting right next to a brilliant poet (Sharon Hopkins) when designing early versions of Perl at JPL in the early 1990s and being led astray by her beautiful poetry readings.

    The old two-argument form of open is subject to various security exploits as described at Opening files securely in Perl.

Re^3: Reading two text files parallelly...
by Marshall (Canon) on Nov 09, 2010 at 16:13 UTC
    With open (FH, "<$file1") or die "blahblah"; there is a possible security issue because maybe the variable $file1 might contain something that would cause problems. What goes in to the open() function is the interpolated string. You learned right, always use the < or > etc. In your example, if $file1 was ">ImportantFile", the open() will fail because the argument would evaluate to "<>ImportantFile" and open() won't like that filename! If you forgot the "<", then then open to ">ImportantFile" might succeed and it would be deleted or other various bad things could happen.

    So if you use:  open (FH, '<', $file1) || die; putting the file mode explicitly there is a "small" thing that could save you big problems later.

    If you are writing small one or two page programs, using a bare word like FH is no big deal. However, be aware that Perl like C (you have do it this way in C), can use lexical variables for filehandles. So you can open($infile, '<', $somefile)... and pass $infile to a subroutine just like any other Perl variable.

    As far as $! in "die" messages, you might or might not want to put that there. Part of this depends upon how descriptive your part of the "die" message is! Ok, try some code:

    #!/usr/bin/perl -w use strict; open(FH, '<', "bad") || die "your textXXX OS says: $!\n"; while (<FH>){} # prevents warning FH only used once
    See what $! has to say. My OS prints, "your textXXX OS says: No such file or directory". I figure that "your textXXX" is way more important. Something like "can't open Budget.csv" is way more to the point than "No such file or directory"- most of the time the OS text is meaningless for the average user. Also notice what adding the trailing "\n" to the die message does.

    Update: This thread has morphed into something else from the OP's original question. But I figure it is ok to comment on some of the comments to the comments!

      Thank you eyespoplikeamosquito and Marshall, definitely cleared that up for me.