Syntax understanding problem

Discussion in 'Perl Misc' started by Justin C, Dec 20, 2013.

  1. It is a kind of term, an expression in parentheses, and it will be
    interpreted based on its context. The +-operator enforces a scalar
    context for both of its operands. But the result of

    ($a = 23) + 1

    is really the same as the result of

    ($b = 24, $a = 23) + 1

    Grammatically (5.10.1),

    term : termbinop

    [...]

    | '(' expr ')'
    { $$ = sawparens(IF_MAD(newUNOP(OP_NULL,0,$2), $2));
    TOKEN_GETMAD($1,$$,'(');
    TOKEN_GETMAD($3,$$,')');
    }

    expr : expr ANDOP expr

    [...]


    | argexpr %prec PREC_LOW


    /* Expressions are a list of terms joined by commas */
    argexpr : argexpr ','

    which is the 5.10.1 'list production'.
     
    Rainer Weikusat, Jan 1, 2014
    #21
    1. Advertisements

  2. Justin C

    Justin C Guest

    I don't know what OP_LIST and pp_list mean. I've googled and
    nothing becomes clearer.


    Justin.
     
    Justin C, Jan 3, 2014
    #22
    1. Advertisements

  3. As Ben already wrote, these are terms from the Perl source code. The
    second of the text was intended to be the more important part. A list as
    it appears in some Perl source code,

    /^something/ and $a = 1, $b = 2;

    is translated to a function call,

    /^something/ and list($a = 1, $b = 1);

    list is an internal function which looks like this (except that it is
    really implemented in C and manipulates the Perl stack directly)

    sub list
    {
    return wantarray() ? @_ : $_[$#_];
    }

    IOW, the comma-separated terms in a 'free hand list' are really nothing
    but comma-separated terms appearing in the argument list of a function
    call and behave in the same way: They are all evaluated and produce a
    value (if they produce a value, eg, a 'next' would cause a control
    transfer instead) and the (internal) list function processes these
    values (Sort of. It returns them unchanged in list context and returns
    its last argument in scalar context).
     
    Rainer Weikusat, Jan 3, 2014
    #23
  4. Justin C

    Tim McDaniel Guest

    A little more on lists and assignments.

    There was a discussion at work that touched on the difference between
    "array" and "list". There was an assertion along the lines of "lists
    *do not exist* in scalar context". In composing a reply, including
    why I don't agree with that mental model, I tried this (lots of
    extraneous stuff there from previous versions):

    $ perl -e 'sub foo {13} sub bar { 14 } sub baz { @a = (5,6,7); @a }; (1 ? $x : @y) = (foo(), bar(), baz()); print $x, "\n"'

    I was hoping that it would show that the list on the right could be
    evaluated either in a scalar or a list context. But the parens needed
    around the ?: operator made it a list LHS, so the RHS was evaluated in
    a list context, so it prints

    13

    just as if I'd written "($x) = (13, 14, 5, 6, 6);".

    Only after I rechecked "man perlop" did I realize that ?: has higher
    precedence than =, so the parens weren't necessary.

    $ perl -e 'sub baz { @a = (5,6,7); @a }; 0 ? $x : @y = (13, 14, baz()); print "x=$x", ", y=", join(" ", @y), "\n"'
    x=, y=13 14 5 6 7
    $ perl -e 'sub baz { @a = (5,6,7); @a }; 1 ? $x : @y = (13, 14, baz()); print "x=$x", ", y=", join(" ", @y), "\n"'
    x=3, y=

    But then I tried with a variable, in a test program

    sub baz { my @a = (5,6,7); @a };
    foreach (0, 1) {
    $_ ? $x : @y = (13, 14, baz());
    print "x=$x", ", y=", join(" ", @y), "\n";
    }
    exit 0;

    I got the error
    Assignment to both a list and a scalar at local/test/117.pl line 3, near ");"
    Apparently 1?: and 0?: did compile-time constant folding and avoided
    the problem.

    The ": lvalue" attribute for a sub only allows a SCALAR lvalue, so
    I can't bury the conditional in a sub.

    So I don't know of any way to write
    ... something ... = (13, 14, 5, 6, 7);
    in Perl so that it doesn't know at compile time whether the right-hand
    side is in a scalar or list context.

    But
    sub foo {
    return (1, 2, 5, 3);
    }
    doesn't know from just that code what the context is, so I think this
    sub is enough of an example that it's not so useful to say "lists do
    not exist in scalar context": I aver that it's better to think that
    there's a list there, and in a scalar context it is evaluated to its
    last element.
     
    Tim McDaniel, Feb 13, 2014
    #24
    1. Advertisements

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments (here). After that, you can post your question and our members will help you out.