lwall@jpl-devvax.jpl.nasa.gov (Larry Wall) (03/14/91)
In article <28041@fs2.NISC.SRI.COM> cwilson@NISC.SRI.COM (Chan Wilson [Animal]) writes:
: &input($labeltype) || {&Bzzzt; &WhatToPrint;}
: ^^^^^^^^^^^^^^^^^^^^^^^^^ offending part
: }
A BLOCK is not an expression. To evaluate a BLOCK as part of an
expression you have to put a do in front of it:
&input($labeltype) || do {&Bzzzt; &WhatToPrint;}
: Naturally, I discovered that I can't do that. So I rewrote a few
: things:
:
: sub Bzzzt {
: print stderr "\n\007<Bzzzt> I need an answer here...\n\n";
: do $_[0];
: }
:
:
: sub WhatToPrint {
: [.....]
: &input($labeltype) || &Bzzzt(WhatToPrint);
:
:
: which had the _very_ interesting aspect of re-entering WhatToPrint at
: the next executable line. It looks like this is another facet of the
: next bug.
Not really.
This code is not doing what you want at all--it's looking for a file called
WhatToPrint to evaluate, and not finding it, and returning. You should
have said
local($subname) = @_;
do $subname();
The parens are required with do. I discourage people from calling subroutines
with do any more for just this reason. & doesn't require parens:
local($subname) = @_;
&$subname;
: But the elegent (IMHO, naturally) thing is what I came up with next.
: I restored Bzzzt to original, and without really thinking, re-wrote
: WhatToPrint to say:
:
: sub WhatToPrint {
: [.....]
: &input($labeltype) || &Bzzzt && &WhatToPrint;
:
:
: which reads as "Do sub input with $labeltype. if 0 is returned, do
: Bzzzt _AND_ do WhatToPrint", which is what I intended, but certainly
: not what perl is interpreting it as.
That's precisely what perl is interpreting it as, as long a Bzzzt returns
a true value, which the print conveniently supplies. Remember that &&
has higher precedence than ||, so it naturally groups the same as
&input($labeltype) || (&Bzzzt && &WhatToPrint);
: Interesting, no? Seems to me this is a way around the `mumble || {foo}'
: restriction...
That's one way to do it. You also could have just said
&input($labeltype) || (&Bzzzt, &WhatToPrint);
But why use recursion when simple iteration will do?
until (&WhatToPrint, &input($labeltype)) { &Bzzzt; }
Larry