First, please note that I ask this question out of curiosity, and I'm aware that using variable names like @@
is probably not a good idea.
When using doubles quotes (or qq
operator), scalars and arrays are interpolated :
$v = 5; say "$v"; # prints: 5 $@ = 6; say "$@"; # prints: 6 @a = (1,2); say "@a"; # prints: 1 2
Yet, with array names of the form @
+special char like @@
, @!
, @,
, @%
, @;
etc, the array isn't interpolated :
@; = (1,2); say "@;"; # prints nothing say @; ; # prints: 1 2
So here is my question : does anyone knows why such arrays aren't interpolated? Is it documented anywhere?
I couldn't find any information or documentation about that. There are too many articles/posts on google (or SO) about the basics of interpolation, so maybe the answer was just hidden in one of them, or at the 10th page of results..
If you wonder why I could need variable names like those :
The -n
(and -p
for that matter) flag adds a semicolon ;
at the end of the code (I'm not sure it works on every version of perl though). So I can make this program perl -nE 'push@a,1;say"@a"}{say@a'
shorter by doing instead perl -nE 'push@;,1;say"@;"}{say@'
, because that last ;
convert say@
to say@;
. Well, actually I can't do that because @;
isn't interpolated in double quotes. It won't be useful every day of course, but in some golfing challenges, why not!
It can be useful to obfuscate some code. (whether obfuscation is useful or not is another debate!)
Interpolation: The variable parsing is allowed when the string literal is enclosed with double quotes or with heredocs. Single quoted string or nowdocs, does not supports variable interpolation.
In computer programming, string interpolation (or variable interpolation, variable substitution, or variable expansion) is the process of evaluating a string literal containing one or more placeholders, yielding a result in which the placeholders are replaced with their corresponding values.
An interpolated string is a string literal that might contain interpolation expressions. When an interpolated string is resolved to a result string, items with interpolation expressions are replaced by the string representations of the expression results. This feature is available starting with C# 6.
Syntax of string interpolation starts with a '$' symbol and expressions are defined within a bracket {} using the following syntax. Where: interpolatedExpression - The expression that produces a result to be formatted.
Unfortunately I can't tell you why, but this restriction comes from code in toke.c
that goes back to perl 5.000 (1994!). My best guess is that it's because Perl doesn't use any built-in array punctuation variables (except for @-
and @+
, added in 5.6 (2000)).
The code in S_scan_const
only interprets @
as the start of an array if the following character is
@x
, @_
, @1
), or:
(e.g. @::foo
), or'
(e.g. @'foo
(this is the old syntax for ::
)), or{
(e.g. @{foo}
), or$
(e.g. @$foo
), or+
or -
(the arrays @+
and @-
), but not in regexes.As you can see, the only punctuation arrays that are supported are @-
and @+
, and even then not inside a regex. Initially no punctuation arrays were supported; @-
and @+
were special-cased in 2000. (The exception in regex patterns was added to make /[\c@-\c_]/
work; it used to interpolate @-
first.)
There is a workaround: Because @{
is treated as the start of an array variable, the syntax "@{;}"
works (but that doesn't help your golf code because it makes the code longer).
Perl's documentation says that the result is "not strictly predictable".
The following, from perldoc perlop
(Perl 5.22.1), refers to interpolation of scalars. I presume it applies equally to arrays.
Note also that the interpolation code needs to make a decision on where the interpolated scalar ends. For instance, whether
"a $x -> {c}"
really means:"a " . $x . " -> {c}";
or:
"a " . $x -> {c};
Most of the time, the longest possible text that does not include spaces between components and which contains matching braces or brackets. because the outcome may be determined by voting based on heuristic estimators, the result is not strictly predictable. Fortunately, it's usually correct for ambiguous cases.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With