unless (open (QTREES, $file)) {
print STDERR "WARNING: get_qtrees() can't open $file for filer $fi
+ler!\n";
return;
};
As a matter of technique, I would write that as:
open my $QTREES, '<', $file or die "WARNING: get_qtrees() can't open '
+$file' for filer $filer!: $!\n";
First, note the addition of
$! in the error message to tell you why the open failed.
Rather than returning with a warning, I have used die.
Using die is usually preferable to printing a warning and continuing because if the open fails, there is usually little point in continuing (aka fail fast). Note that die throws an exception, so you can always catch that and not exit the program by wrapping the subroutine call in an eval block in the rare case that you want to continue after the open fails. As an alternative, you could first check via -f $file that the file exists and return with a warning if it does not exist and die only if it exists yet the open fails
(update: see below and How portable are common $! error codes? for a race-condition-free alternative).
Using lexical file handles (i.e. my $QTREES above) 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 and should be avoided (except when writing poetry).
Oh and be sure to start your programs with "use strict;" (just in case you are not doing that already).
Finally, note that I used the three-argument form of open.
As for why the three-argument form of open is preferred, the
old two-argument form of open is subject to various security exploits as described
at Opening files securely in Perl.