Re: Re^4: Determining what line a filehandle is on
by sierrathedog04 (Hermit) on Jul 06, 2001 at 17:17 UTC
|
Larry Wall compares $_, which is also magical, to the pronoun "it." Generalizing we can say that all magical variables of this kind are pronouns, e.g., "he", "she", "thou" etc.
One of the great things about Perl is that Larry Wall when explaining it uses ideas from linguistics. Pronouns exist in all spoken languages that I know of for a reason. They avoid repeating obvious information in a way that reduces readability.
It may be true that the "average" Perl programmer may not know all of the magical variables by heart, but he knows that an unusual short dollar sign symbol is a magical variable. Stripping the more arcane special variables out of Perl is like decreeing that from now on no one should use the word "thou" when speaking to others. "To every thing there is a season" (King Solomon/Pete Seeger/Crosby and McGuinn) | [reply] |
|
Someone once told be a bit of wisdom: "Just because you can
doesn't mean you should".
$. gets the job done, and it works consistently in a
logical fasion. However, it's a shortcut, and it's not
strictly necessary. If you want to show off, or you are
in a tremendous rush where every keystroke counts because
you are just doing something simple with -e, then by all
means, use variables like it.
If you want to write something that is useful and comprehensible
to others, be a sport and keep it simple.
If your favorite author suddenly started to use a heavy
helping of very obscure words in their writing,
would you go through all the trouble to look each and
every one up? Does using fancy words make for a better
book, or does it just make the author seem like some kind
of deranged thesaurus addict?
In Code Complete, which frowns on "fancy code"
heavily, an example given is the ?: operator which is
fairly easy to understand, but can get way out of hand
if used to an extreme. You can lose track of the meaning
of the code even though it works:
if ($foo?$x?($y|$a<<2):$s&$z?$x==$v:0:$c) { ...
That might be the slickest, most compact, fastest executing
way of expressing your particular problem, but to most
people, it is going to be virtually impossible to find
a problem with it. In some cases, "other people" means
yourself a few years down the road when you've nearly
forgotten how the program worked, yet have to fix a slight
bug that was discovered.
Express it in a manner that is as simple as possible, but
no simpler.
| [reply] [d/l] |
|
I think your sample code is great in that it shows just how well the variable $. works when used correctly (in that if you are working with two filehandles, it really does work just like a pronoun by referring only to the most recently handled file).
But I don't think $. is fancy code, any more than I think using
sub my_func {
my $arg1 = shift;
my $arg2 = shift;
...
}
is fancy code for using an implied $_ in the argument assignements. $. is there so I, as a programmer, don't have to add code (and potentially bugs) to the process of counting which line I am on in a file, and as such it may help to make programs work better. I would say that using $. more than a couple of lines away from the filehandle is a bad idea-- same rules as for pronouns in spoken language. | [reply] [d/l] |
Re: Re^4: Determining what line a filehandle is on
by John M. Dlugosz (Monsignor) on Jul 07, 2001 at 21:11 UTC
|
matt brings up a good point back on the main thread, that $. will count correctly even when the special <> magic handle moves from file to file. Doing that yourself means testing eof in your loop too, and complicating things.
Update:Well, it seems that $. doesn't reset on each file normally. You need to add a close ARGV if eof;statement inside the loop anyway!
But, your argument is that the magic <> is obsure so you shouldn't use that either—with so much magic and subtlety, “to the average programmer, especially one not intimately familar with Perl, is that they don't make any sense.”
But it does something so useful that would be a lot of code to do yourself! The program would be harder to figure out, and possibly buggy, if you did it yourself. And if all that code was put into a module and you got it down to a single function call, well, that's just what <> does in the first place.
So, given the sentiment that obscure things can make it difficult for maintaniance, where do you draw the line? Answer: how easy is it to look up? If the obscure thing is some idiom spread over a few lines, and you don't know the name of it, how do you look it up anywhere? But a particular function call or special variable is easy to look up in the manual under that name. In the former case, always use a comment that could be as simple as naming the construct, e.g. "sort using the or-cache maneuver".
—John | [reply] [d/l] [select] |
Re: Re^4: Determining what line a filehandle is on
by John M. Dlugosz (Monsignor) on Jul 07, 2001 at 05:08 UTC
|
I agree with the reply that the magical variables all have a recognisable form, so that a programmer might not know what $. or $] means, but knows it is one of those magical variables and can look it up.
However, calling $input->input_line_number() is quite clear, and according to the docs, is a true method that works on the object called with, rather than doing something counterintuitive like input_record_separator() which is actually global.
What do you mean by "makes things more difficult to implement"? You mean in general, or because this simple task is so small it's not with the overhead?
—John | [reply] [d/l] [select] |
|
It's not terribly more difficult, but slightly. More wear
on the fingers, use of modules, etc, but the result is
crystal clear. Not the kind of thing you would do in a
quick '-e', but if you want to communicate, this is the
only way to fly:
use IO::Handle;
open ($a, "ls|");
open ($b, "ls|");
while (<$a>)
{
print "A: ", $a->input_line_number(), " ";
<$b>;<$b>;
print "B: ", $b->input_line_number(), " ";
}
close ($a);
close ($b);
| [reply] [d/l] |
|
Given that $a and $b are special to sort it is a bad
idea to use them as regular variables.
Also note that if you are willing to properly localize them
with my, then you should not need to issue an explicit
close. Of course declaring $a or $b to be lexical makes
writing a sort subroutine hard (hence the first piece of
advice).
Finally I think your "only way to fly" comment is a bit
strong...
| [reply] |
|
|
$a= undef;
open ($a, "<file.txt");
a fairly new thing? That is, we used to have to use tricks to create a reference to an anonymous filehandle first, and then open it. Now filehandles are autovivafing. I think that may be one reason why getting away from plain HANDLE's is historicaly a pain, but isn't as bad anymore. | [reply] [d/l] |
|
|
|