There's strictly no warranty for the correctness of this text. You use any of the information provided here at your own risk.
This site lists recurring questions and patterns, when programming Perl, especially in an object-oriented way as described on my other page.
It addresses people who already know the basics of Perl-programming.
If you want to declare multiple "my"-variables in one line, separate them with commata and put round brackets around them:
#!/usr/bin/perl use warnings; use strict; my ($i, $u, @a, @b);
If you want to declare global variables, use this line:
use vars qw($i $u @a @b);
You can use the qw-operator to quickly build a list from elements. The elements have to be written without quotation marks and have to be separated by space characters:
#!/usr/bin/perl use warnings; use strict; my @a = qw(Hello good World); for my $i (@a) { print "$i\n"; }
To cycle through the element-numbers of a list, you can use this pattern:
#!/usr/bin/perl use warnings; use strict; my @a = qw(Hello good World); for my $i (0 .. $#a) { print "$i \t $a[$i] \n"; }
Notice, that "$#a" is the "number of elements of @a minus 1". For whatever reason they build that into Perl.
#!/usr/bin/perl use warnings; use strict; my $a = "214314"; if ($a =~ /\D/) { print "Contains something else than digits.\n"; } else { print "Only digits. String contains a number.\n"; }
"@ARGV" is the list, that contains the options, passed to the Perl-script on the command-line.
"@ARGV" doesn't contain the name of the script as the first element (as Python's "sys.argv" does). Therefore, "$#ARGV" is -1, if the user didn't pass any option to the script.
In Perl, there are five functions to add elements to lists or withdraw elements from them:
When you call a function, in Perl all arguments are automatically passed in a single list called "@_":
#!/usr/bin/perl use warnings; use strict; sub myFunction { for my $i (@_) { print "$i\n"; } } myFunction("Hello", "World");
If you want to assign variable-names to the arguments, you have to get them from this special array. If the shift-function is called without any parameter, Perl assumes, that the array "@_" is meant. So you can extract the arguments inside the function like this:
#!/usr/bin/perl use warnings; use strict; sub myFunction { # Short for "my $a = shift(@_);": my $a = shift; my $b = shift; print "$a\n"; print "$b\n"; } myFunction("Hello", "World");
At first sight, the mechanism explained above makes it difficult to pass scalar variables and lists or hashes to functions at the same time.
If you know, that the first element of "@_" represents a scalar variable, and the rest of "@_" represents a list, you could shift the first element of "@_" away and assign the rest to a list-variable.
But there's a more elegant solution: You can pass references to lists or hashes to the function and dereference them in a single line. Here's an example:
#!/usr/bin/perl use warnings; use strict; sub myFunction { my $a = shift; my @b = @{shift(@_)}; for my $i (@b) { print "$i\n"; } } my $a = "test"; my @b = ("Hello", "World"); myFunction($a, \@b);
The line of the dereferencing
my @b = @{shift(@_)};
may look a bit ugly, but it's rather straight-forward:
"shift(@_)" extracts the list-reference from "@_", then "@{listref}" dereferences it. The variable "@b" is assigned to the resulting list.
The best practice for creating multi-line comments is probably this one:
=begin comment This is a comment, that is longer than one line. Such comments are for example used to describe the features of a program at the beginning of the code. =end comment =cut
It may be useful to put longer strings, that contain a lot of quotation marks, inside q() or qq().
q( ... ) is similar to ' ... ',
qq( ... ) is similar to " ... ".
Example:
#!/usr/bin/perl use warnings; use strict; my $string = qq(This is one of Perl's features for long strings. The string is longer than one line and contains "quotation marks". But you don't need to write backslashes in front of them. If you use qq(), there also is \t interpolation.\n); print $string;
You can also use socalled "here-documents" in Perl.
To do that, you define a variable with "<<" and then a sequence of characters, like "END_MESSAGE" or "HERE" for example. After that, the following characters are defined as a string, which ends at another occurrence of the defined sequence of characters:
#!/usr/bin/perl use warnings; use strict; my $message = <<'END_MESSAGE'; This is another string, that is longer than one line. END_MESSAGE print $message;
For comments, it still may be best to use "#" before each line.
You can use scalar variables within regular expressions.
But if you just use something like
if ($a =~ /$b/) {...}
variable $b will be interpolated. That means, if $b contains characters, that have a special meaning in regular expressions (such as "*", "." or "!") they will be interpreted with that meaning.
That may not be, what you want, if you literally want to search for "Hello, there!" for example. To suppress the interpolation of $b, you have to put it between "\Q" and "\E" inside the regular expressions (which may seem a bit strange at first, but you'll get used to it). Here's an example:
#!/usr/bin/perl use warnings; use strict; my $a = "House"; my $b = "^H"; if ($a =~ /$b/) { print "String starts with a \"H\".\n"; } if ($a =~ /\Q$b\E/) { print "'^H' found in string.\n"; } else { print "Substring '^H' not found in string.\n"; }
Text after the word "__DATA__" or the word "__END__" is ignored as Perl-code (so that the words indicate the end of the actual script), but can be read in as data, using the built-in filehandle called "DATA":
#!/usr/bin/perl use warnings; use strict; my @a = <DATA>; for my $i (@a) { print $i; } close(DATA); __END__ This is one of Perl's features for data, such as long strings. The data consists of several lines, that can be read into a list. It can be processed afterwards.
Functions like sort, lc (lowercase) and uc (uppercase) don't work in place. So you have to reassign the variable like in:
@a = sort(@a);
The module "Data::Dumper" is used to print the contents of more complex data-structures, such as "Lists of Lists", "Hashes of Hashes" (HoH) and such:
#!/usr/bin/perl use warnings; use strict; use Data::Dumper; my %h = ( a => ["z", "x", "y"], b => "test", c => { d => 1, e => 2, f => 3 } ); print Dumper(\%h);
"Dumper" is imported into the script's namespace. It is called with a reference to the variable to be printed (otherwise it would see the parts inside the variable as separated variables).
"Data::Dumper" can also be used to print the contents of objects.
My little series about Perl continues with "Perl Page #5: Tips and Tricks".