2

I have to expressions:

%MON =    months => 1, end_of_month => 'limit';      # months => undef
%MON =  ( months => 1, end_of_month => 'limit' );

Why first expression results only one key months with undef value? What is the difference between them?

Artjom B.
  • 61,146
  • 24
  • 125
  • 222
Eugen Konkov
  • 22,193
  • 17
  • 108
  • 158

2 Answers2

5

See perlop. = has higher precedence than =>

%MON =    months => 1, end_of_month => 'limit'; 

Is equivalent to:

(%MON = "months"), 1, "end_of_month", "limit"

While:

%MON =  ( months => 1, end_of_month => 'limit' );

is:

%MON = ("months", 1, "end_of_month", "limit")
Quentin
  • 914,110
  • 126
  • 1,211
  • 1,335
2

Here's Perl's table of operator precedence (from perlop):

left        terms and list operators (leftward)
left        ->
nonassoc    ++ --
right       **
right       ! ~ \ and unary + and -
left        =~ !~
left        * / % x
left        + - .
left        << >>
nonassoc    named unary operators
nonassoc    < > <= >= lt gt le ge
nonassoc    == != <=> eq ne cmp ~~
left        &
left        | ^
left        &&
left        || //
nonassoc    ..  ...
right       ?:
right       = += -= *= etc.
left        , =>
nonassoc    list operators (rightward)
right       not
left        and
left        or xor

Notice that = has higher precedence than either , or =>. Therefore, you need the parentheses to override the precedence.

Dave Cross
  • 68,119
  • 3
  • 51
  • 97
  • Should `=` have less precedence when is used at `void` context? – Eugen Konkov Nov 27 '20 at 18:10
  • 2
    @Eugen Konkov, You can't determine the context of an operator until you determine which operator is an operand of which. Parsing must necessarily happen before the context of the resulting pieces is determined. For example, the `=` in `A = B && C; 1` is evaluated in void context, but the `=` in in `A = B and C; 1` is evaluated in scalar context, and you only know that because of precedence. /// There's also the issue that the context of the the last statement of a function and of a return expression isn't know until runtime, so it couldn't possibly affect how code is compiled. – ikegami Nov 27 '20 at 18:48