[Edinburgh-pm] a Perl surprise

Jeff Parsons bynari at gmail.com
Wed Jul 18 11:12:47 PDT 2012

On 18/07/2012 18:31, Nick wrote:
> True, but I think you mentioned 'array context', not me... :)

I was just pointing that out as a reminder in case you didn't know. :-) 
I didn't think you were new to Perl, but sometimes people do think 
there's an array context.

> To be honest, the quotes were an afterthought. The real point of that example is
> the double brackets.    wtf(6, 7, 8) gets a compilation error.  wtf((6, 7, 8))
> does not. And wtf qw(6 7 8) does not either, because of a diabolical combination
> of Perl's grammar rules.

Ah right, it gets a compilation error, yeah, that makes sense. Really 
what we have is the comma operator in scalar context, thus producing the 
8 just like $foo = (6, 7, 8).
> In agreement with General Wisdom, I also tend not to use prototypes, except
> perhaps things like (&@).  However in this case I was attempting to use the ($)
> prototype to try and force a function not to be "greedy", and instead consume
> just one single argument.  The application is a configuration language - I'm
> trying to warp Perl into a DSL.
>     # (checks and balances elided)
>     sub with($) { bless $_[0], 'With' }
>     sub without($) { bless $_[0], 'Without' }
>     sub combination { ... }
>     # ...
>     my $combination = combination (
>        with [qw(toast eggs)],
>        without ['gluten'],
>        with [qw(sauce)],
>     );
> I could lose the square brackets and the prototypes and wrap everything in
> brackets to coerce the functions to eat the right things:
>    with (qw(toast eggs)), without('gluten'), with(qw(sauce))
> But I wanted it to be robust so that if the brackets were forgotten, things
> would fail safely rather than grouping in unintended ways.  (No, I'm not
> convinced my alternative is entirely better, but... this is an experiment.)
> Also in the name of robustness, I want to highlight potential accidental misuses
> of 'with' and 'without', such like this:
>    combine with qw(toast egg), without qw(gluten);  # Error: 'toast' not eaten
> Bad syntax should fail instead of doing something surprising. Except to my
> annoyance, this gave me something even more surprising as discussed:
>    my $stuff = combine with qw(toast eggs), without qw(gluten);
> Here, 'with' gets 'eggs', but 'toast' gets discarded on the floor, a somewhat
> obscure warning about void context gets printed, and things charge onwards to
> disappointment and/or disaster.  Not good.

Eek. Robustness isn't about stopping other programmers from making 
syntax errors. Robustness generally is where software will catch a lot 
of issues and do plenty of checks. Ie, software that's not robust just 
makes a whole bunch of assumptions about the data it's working with, 
then things can just mysteriously go wrong. Robust software checks 
*everything* and then informs the user/programmer if it has something it 
didn't expect. Robustness is for preventing the programmers/users from 
misusing an interface, not for preventing them from making syntax errors.

If a programmer using your interface forgets brackets then I think 
they're going to have a whole bunch of problems beyond the scope of what 
you're trying to prevent!! :-)

Gosh, they'd have to be pretty new to Perl to do "combine with toast 
egg, without gluten;"

If someone's doing that then they need to hit the Perl books at chapter 1!

Your module will be more robust by having the checks that you can't have 
toast without gluten(Although you actually can have gluten-free bread, lol!)

You should only develop with an intention to prevent programmers from 
passing incorrect/incompatible things to your interface, not things to 
prevent them from making potential syntax errors.

Definitely just stick with passing a list then shift'ing in the method. 
An arrayref is superfluous. You'd only ever want to use an arrayref if 
you wanted to separate out 2 lists. I'm sure you already know that 
though, but I'll just state it anyway. :)

>> Regards,
>> Geoff
> You seem to be both Geoff and Jeff simultaneously?

Yes, indeed. I'm magical. :-)

More information about the Edinburgh-pm mailing list