A Look At Braces
In a comment of an article here at blogs.perl.org, Going to Perl School, I mentioned that Perl has 9 uses for braces. Here they are:
- 1. BLOCK
The first one is easy: Perl uses braces to delimit blocks of
code.This may be to provide isolation. For example to slurp a file:
open my $fh, '<', $some_file or die $!;# have to declare lines outside of the block
# or it will be dropped at the end
my $lines;{
# set the input record separator to undef,
# see `perldoc perlvar`
# and search for /INPUT_RECORD_SEPARATOR/
local $/;$lines = <$fh>;
}
close $fh or die $!;
Blocks must be used with the compound statements like "http://perldoc.perl.org/perlsyn.html#Compound-Statements" class=
"podlinkurl">if
, "http://perldoc.perl.org/perlsyn.html#Compound-Statements" class=
"podlinkurl">while
, and "http://perldoc.perl.org/perlsyn.html#Compound-Statements" class=
"podlinkurl">for
. They are also used with commands
like "podlinkurl">map
and "http://perldoc.perl.org/functions/grep.html" class=
"podlinkurl">grep
.
- 2. Hash Keys
Braces are used with a hash to access the value.
print $hash{$key};
- 3. Anonymous Hashes
Braces are used to create anonymous hashes.
my $hash_ref = { foo => 'bar' };
- 4. De-referencing
Braces are used in de-referencing, especially for arrays and
hashes.
for my $item ( @{ $obj->{list} } ){
# ...
}for my $key ( sort keys %{ $obj->{config} } ){
# ...
}
- 5. File Handles
Isolation
Braces are used to to isolate a file handle.
print {STDERR} "Error detected.\n";
This is the only way to use a file handle in a data structure.
print {$object->{out_fh}} "Error detected.\n";
- 6. Quote Delimiters
"http://perldoc.perl.org/perlop.html#Quote-and-Quote-like-Operators"
class="podlinkurl">Generic quotes can be delimited with braces.
my $SPACE = q{ };
my $NL = qq{\n};s{ \A \s+ }{}msx;
s{ \s+ \z }{}msx;
- 7. Delimiters in
String Interpolation
Braces are use in string interpolation to create special characters
and to delimit them from the rest of the text.
"\o{033}"
"\x{1b}"
\N{ESC}""\x{2022}"
"\N{U+2022}"
They are also used to separate a variable name from other
alphanumerics.
print "Using temporary file ${src_file}_tmp";
- 8. Regular Expression
Quantifiers
In regular expressions, braces are used for specifying quantifiers
of matches.
# look for two or more underscores
if( m{ _{2,} }msx ){
# ...
}
- 9. Regular
Expression Embedded Code
Code can be embedded in regular expressions in the newer versions of
Perl.
perl -nE'm{ ( [aeiou] ) (?{ say "$1" }) }msx'
I always thought of #5 "File Handles Isolation" as the same as #1 "BLOCK".
Just like
map BLOCK LIST
, we haveprint BLOCK LIST
whereBLOCK
returns a filehandle.print { $o->err ? STDERR : STDOUT } $o->msg, "\n";
Pretty sure that "they are also used to separate a variable name from other alphanumerics" is the same thing as #4.
And here's one to add... sometimes braces are just braces! e.g.
my $braces = q({})
You could be correct. The `perldoc -f print` doesn't list the BLOCK as a possibility, so I overlooked it.
No, in #4, the expression in the braces evaluates to a reference. In string interpolation, the contents are placed in the string. If the contents is a reference, then a weird value appears in the string, like, "SCALAR(0x1f39838)".
You're correct; sometimes a brace is just a brace.
It seems to me that
perlfunc
should be updated as such:print BLOCK LIST
print FILEHANDLE LIST
print FILEHANDLE
print LIST
print
It's interesting that braces are more polymorphic in Perl than most other languages yet many of Perl's operators are less polymorphic than many other languages, which I personally prefer. I've found that braces are the most confusing part of Perl syntax for new developers and I think that polymorphism is a big part of the issue, as well as referencing/dereferencing being a tricky concept for the uninitiated.
It just came to me, this post should have been entitled "A brace of kinsmen".
Here's another one: iteration in globbing.