—A—

Apache, make so it know what to do with .pl files – see pl file, make apache know what to do with

arguments to a program - $ARGV[0], etc.

#!/usr/bin/perl -w

# check if we have 2 arguments:

die "USAGE: add number1 number2\n" unless ($ARGV[1]);

print "$ARGV[0] + $ARGV[1] is:", $ARGV[0] + $ARGV[1] ,"\n";

arrays

array, append to – see push

array, clear - @array = ();

array, compare two to see whether same or not –

foreach (@a)

{

    if ($a[$i] eq $b[$i]) {print " $a[$i] is different from $b[$i] at $i."; last}

    $i++;

}

array, length of –

evaluate @array in scalar context such as @array + 1 or just refer to it as @array

scalar(@array)

$#array will return the subscript of the last element of the array, or one less than the length, since there is (ordinarily) a 0th element

array, loop through

for my $var (@loop)

{

print "$var in words is ${$a_2}[$var-1]\n";

}

array, move item in the middle of a array to the front

best way:

@values = grep ($target, { $_ ne $default } @values)

another way:

for (my $i = 0; $i < @values; $i++)

{

    if ($values[$i] eq $target)

    {

         splice (@values, $i,  1);

         unshift (@values, $target);

         last;

    }

}

yet another way, in the context of generating an HTML select list:

my $returnHTML =

     popup_menu (-name => $name, -values => \@values, -default => $default)

sample code for array manipulations

array of arrays, sort

@final = sort { $a->[0] cmp $b->[0]} @LoL;

 

for $name (@final) {

  print "$name->[0] $name->[1]\n";

 

}

Notice that @final is getting copies of the references to the data.  After the call to sort(), @final and @LoL will be two arrays pointing to the same data.  Here’s a better way that only takes one step, without using an intermediary array:

foreach my $thisAddrRef (sort {

                            $a->[-1] cmp $b->[-1] or    # zip

                            $a->[2] cmp $b->[2] or      # addressee

                            $a->[3] cmp $b->[3] or      # addr1

                            $a->[4] cmp $b->[4] or      # addr2

                            $a->[5] cmp $b->[5]         # addr3

                           } @allAddr)

{

    my @thisAddr = @$thisAddrRef;

}

array, pass several arrays as an argument to a subroutine – pass the arrays as a reference. For example:

my @arr1 = (1, 2, 3, 4);

my @arr2 = ('One', 'Two', 'Three', 'Four');

 

&mysub(\@arr1, \@arr2);

 

sub mysub

{

my ($a_1, $a_2) = @_;

for my $var (@{$a_1})

{

print "$var in words is ${$a_2}[$var-1]\n";

}

}

 

Output:

=======

1 in words is One

2 in words is Two

3 in words is Three

4 in words is Four

array, pass and return several arrays – pass and return the arrays as a reference. For example:

#!/usr/bin/perl -w

use strict;

use warnings;

 

# Subroutine prototypes

sub getAndReturnTwoArrays($$);

 

my @array1 = ("a", "b", "c", "d");

my @array2 = (1, 2, 3, 4);

 

# Get two variables back

my ($one_ref, $two_ref) = getAndReturnTwoArrays(\@array1, \@array2);

 

my @one = @$one_ref;

my @two = @$two_ref;

print "First: @one\n";

print "Second: @two\n";

 

sub getAndReturnTwoArrays($$)

{

      ($one_ref, $two_ref) = @_;

      my @array1 = @$one_ref;

      my @array2 = @$two_ref;

      push (@array1, 'g');

      push (@array2, 5);

    return (\@array1, \@array2);

}

array, return several arrays as arguments from a subroutine – return the arrays as a reference. For example:

If you can arrange for the function to receive references as its parameters and return them as its return results, it's cleaner code, although not so nice to look at. Here's a function that takes two array references as arguments, returning the two array references ordered according to how many elements they have in them:

 

($aref, $bref) = func(\@c, \@d);

print "@$aref has more than @$bref\n";

sub func {

    my ($cref, $dref) = @_;

    if (@$cref > @$dref) {

        return ($cref, $dref);

    } else {

        return ($dref, $cref);

    }

}

#!/usr/bin/perl

use strict;

use warnings;

 

# Subroutine prototypes

sub get_two_arrays();

 

# Get two variables back

my (@one, @two) = get_two_arrays();

 

print "First: @one\n";

print "Second: @two\n";

 

sub get_two_arrays() {

    my @array1 = ("a", "b", "c", "d");

    my @array2 = (1, 2, 3, 4);

    return (@array1, @array2);

}

array, slice – see slice array

—B—

break out of a loop – see loop, break out of

—C—

clear array – see array, clear

code examples

cgiscript

command line, pass argument to a program from - $ARGV[0], etc.

#!/usr/bin/perl -w

# check if we have 2 arguments:

die "USAGE: add number1 number2\n" unless ($ARGV[1]);

print "$ARGV[0] + $ARGV[1] is:", $ARGV[0] + $ARGV[1] ,"\n";

command line, run perl command from –

>perl -e "print 'Hello world!';"

Hello world!

compare two arrays to see whether same – see array, compare two to see whether same

cookies

sub GetCookies{
$cookies = $ENV{'HTTP_COOKIE'};
@allcookies = split(/;\s*/,$cookies);
foreach $i (@allcookies){
($name,$value) = split(/\s*=\s*/,$i);
$cookie{$name}=$value;
}
}

—D—

date of file – see file time stamp

day of year - (undef, undef, undef, undef, undef, undef, undef, $yday) = localtime(time);

(from ($sec, $min, $hour, $mday, $mon, $year, $wday, $yday) = localtime(time);)

debuggers, interactive

ddd – as in ddd --debugger 'perl –d frProjects'

ptkdb – as in #!/usr/bin/perl –d:ptkdb

decimal format, force to 2 decimal places - $formatedX = sprintf ("%.2f\n", $unformattedX);

delimiter – split

directory, read file names out of

#!/usr/bin/perl -w

 

my $dirName = '.';

opendir MAILDIR, $dirName or die "problem: $!";

@allfiles = readdir MAILDIR;

closedir MAILDIR;

foreach $thisFileName (@allfiles)

{

    next if (($thisFileName eq '.') or ($thisFileName eq '..'));

    my $thisFileNameWithPath = $dirName . '/' . $thisFileName;

    print "name: $thisFileNameWithPath\n";

}

download perl.exe - ActivePerl

—E—

embed code in a string - @{[code]}

environment variables, print out all of:

sub PrintErr {

     print "<PRE>\nCGI Error: $!\n";

     print "Message: $_[0]\n\n";

     print "====== Form Variables ======\n";

     foreach $key (sort keys %in) {

       print "$key: \t$in{$key}\n";

     }

    

     print "\n====== Environment Variables ======\n";

     foreach $env (sort keys %ENV) {

       print "$env: \t$ENV{$env}\n";

     }

     print "\n</PRE>";

}

use by: &PrintErr;

escape quotes (HTML) – CGI::escapeHTML()

Excel spreadsheet, write binary - Spreadsheet::WriteExcel

—F—

FAQ

Perl.com (O'Reilly)

Theoryx5

file, redirect output to– if “perlprog” is your program, perlprog > output.txt

file, read

#!/usr/bin/perl

open (CRYPTSMP, "encrypts.txt");

 

while ($record = <CRYPTSMP>) {

       print $record;

   }

or

#!/usr/bin/perl

open (CRYPTSMP, "encrypts.txt");

 

@raw_data=<CRYPTSMP>;

 

foreach $line (@raw_data)

{

     ($username,$seed,$encrypted,$linenum)=split(/\t/,$line);

     print "username: $username\n";

     #print "$line \n";

}

 

close(CRYPTSMP);

close(CRYPTSMP);

file time stamp – use stat – don’t use ctime if you want a raw string to sort on

#!/usr/bin/perl -w

 

use File::stat;         # for mtime

use Time::localtime;    # for ctime

 

my $dirName = '.';

opendir MAILDIR, $dirName or die "problem: $!";

@allfiles = readdir MAILDIR;

closedir MAILDIR;

foreach $thisFileName (@allfiles)

{

    next if (($thisFileName eq '.') or ($thisFileName eq '..'));

    my $thisFileNameWithPath = $dirName . '/' . $thisFileName;

    my $date_string = ctime(stat($thisFileNameWithPath)->mtime);

    print "name & time stamp: $thisFileNameWithPath $date_string\n";

}

fill HTML template - see template, fill HTML

—G—

—H—

Hello World – see also pl file, make apache know what to do with

#!/usr/bin/perl

print "Content-type: text/html\n\n";

print "<html>\n";

print "<head>\n";

print "<title>Hello world with Perl</title>\n";

print "</head>\n";

print "<body>\n";

print "<h1>Hello world with Perl</h1>\n";

print "<p>Howdy, world!</p>\n";

print "</body>\n";

print "</html>\n";

here-document, Use of uninitialized value in concatenation (.) or string – look for uninitialized variables in the body

Host of incoming web user - see IP address, translate to host

HTML quotes, putting into without confusing HTML – CGI::escapeHTML()

HTML template, fill - see template, fill HTML

—I—

IDE - Open Perl IDE

information - see environment variables, print out all of

IP address of incoming web user

$ENV{'REMOTE_ADDR'}

IP address, translate to host

$remote_address = $ENV{'REMOTE_ADDR'};

@subnet_numbers = split (/\./,$remote_address);

$packed_address = pack ("C4",@subnet_numbers);

($remote_host) = gethostbyaddr ($packed_address, 2);

—J—

join an array of hashes –

say you have array of hashes:

$field [0] {name} = "addressID";

$field [1] {name} = "name";

$field [2] {name} = "addr1";

$field [3] {name} = "addr2";

to join,

my $selectClause = join ', ', map {$_->{name}}@field;

join, opposite of split - $string = join ', ', @list;

—K—

—L—

length of array –

evaluate @array in scalar context such as @array + 1 or just refer to it as @array

scalar(@array)

$#array will return the subscript of the last element of the array, or one less than the length, since there is (ordinarily) a 0th element

length of string - $lengthStr = length ($string);

lists – see arrays

loop, break out of

next – skip to end of current loop iteration, start next iteration

last – skip to end block, as if condition had returned false

—M—

manual

modulus – if (5 % 2 == 1) {}

—N—

newsgroups

google - comp.lang.perl.misc

—O—

output, redirect to file – if “perlprog” is your program, perlprog > output.txt

—P—

page that called this script - $ENV{HTTP_REFERER}

parse a variable that has several lines, each line with variable = value, into a hash

use strict;

use as;

use Data::Dumper;

 

use vars qw (

           %myTestHash

           );

 

sub buildHash ($$);

%myTestHash = ();

 

frInit ('joe_support@artselect.com', 'no CGI');

my $tmp =<<"EOF";

something else

var1 => 'value1'

var2 => 'value2'

var3 => 'value3'

EOF

 

print $tmp;

 

my $regExpToParseVarAndValue = '^([^\=]+?)\=> \'([^\']+?)\'$';

$tmp =~ s/$regExpToParseVarAndValue/buildHash ($1, $2)/gme;

frExit (0);

 

sub buildHash ($$)

{

      my ($varName, $varValue) = @_;

 

      print "---------------------------------------------------------\n";

      print "varName = $varName\n";

      print "varValue = $varValue\n";

 

      $myTestHash{$varName} = $varValue;

}

path – from the command line, type: perl -e 'print join "\n", @INC'

pl file, make apache know what to do with

make sure apache-perl is installed

e /etc/apache/httpd.conf (or e /etc/apache2/sites-available/default)

C-s Exec-CGI

Change

# Options Indexes Includes FollowSymLinks MultiViews

to

Options All MultiViews

In the same file, for each <VirtualHost>:

ScriptAlias /cgi-bin/ /var/www/apache2-default/mysite.com/cgi-bin/

    <Directory "/home/mysite.com cgi-bin">

         AllowOverride None

         Options ExecCGI All +MultiViews +SymLinksIfOwnerMatch

         Order allow,deny

         Allow from all

         AddHandler cgi-script cgi pl

    </Directory>

Or whatever other paths in which you want Apache to look for your scripts

e mime.types

/etc/init.d/apache restart

perl /var/www/HelloWorld.pl

chown www-data HelloWorld.pl

position in a string – pos Returns the offset of where the last m//g search left off for the variable is in question ($_ is used when the variable is not specified).

while ($string =~ m/regex/g) {

  print "Found '$&'.  Next attempt at character " . pos($string)+1 . "\n";

}

process id - $$

program arguments - $ARGV[0], etc.

#!/usr/bin/perl -w

# check if we have 2 arguments:

die "USAGE: add number1 number2\n" unless ($ARGV[1]);

print "$ARGV[0] + $ARGV[1] is:", $ARGV[0] + $ARGV[1] ,"\n";

program that's running right now - see script that's running right now

push

to simply append a 1-dimensional array (or scalar) to the end of another 1-dimensional array - push @originalArray, @appendedArray

to push a 1-dimensional array to a 2-dimensional list of 1-dimensional arrays:

#!/usr/bin/perl

 

my @input = ( [1, 2, 3], [4, 5, 6] );

#my @input = ( \@line1, \@line2 );

 

my @data;

my $i = 0;

 

# The 'my' in the loop is imperative, otherwise, each row will erase the

# previous one.

# The braces in @{ ... }  are imperative because of operator precedence

# against the [ ] brackets

while (my @dataRow = @{$input[$i++]}) {

    print @dataRow, "\n";

 

    # This stores a pointer to the @dataRow array, i.e. its address or

    # reference.

    # So essentially, you get an array of addresses of arrays, which

    # effectively gives you an array of arrays.  Note that each sub-array

    # (each row) can be different sizes unlike traditional 2-dimensional

    # arrays.

    push @data, \@dataRow;

}

 

# Now how do we get the data out?

# So in our array of arrays, if you say @data[5] you're saying

# data[5] which you want to be an array.  but that's not the way we

# stored things; we stored things as addresses of (or references to) arrays.

# So you have to say $data[5] to get the address of the array, and use @ to

# get the array, i.e.  @{$data[5]}  This is called dereferencing.

 

print "Output loop\n";

 

foreach (@data) {

    print @{$_}, "\n";

    # I could have this instead, but less clear:

    #print @$_, "\n";

 

    print ${$_}[0], "\n";

    # I could have this instead, but less clear:

    #print $$_[0], "\n";

}

 

# Or equivalently

print "Explicit Output\n";

print @{$data[0]}, "\n";

print ${$data[0]}[0], "\n";

print @{$data[1]}, "\n";

print ${$data[1]}[0], "\n";

push, opposite of – unshift (prepends instead of tacking onto the end)

—Q—

quotes, putting into HTML without confusing HTML – CGI::escapeHTML()

—R—

read file – see file, read

real number, check for –

/^-?\d+\.?\d*$/              – does not like leading 0

/^-?\d*(\.\d+)?$/            – better

redirect output to file – if “perlprog” is your program, perlprog > output.txt

regular expressions – see

parse a variable that has several lines, each line with variable = value, into a hash

require problems (from google posting)

the "compile once, run multiple times" pitfall (indicated by "works about 1 out of every two tries).  Try this:

- run your httpd with the -X switch (daemon won't fork)

- replace "require '/home/httpd/html/stdinc.pl';" with

use lib '/home/httpd/html/';

require 'stdinc.pl'

run perl command from command line –

>perl -e "print 'Hello world!';"

Hello world!

—S—

script that's running right now - $ENV{SCRIPT_NAME}

scope

Coping with Scoping

session management

Apache-Session or here for list of all modules in mod_perl (Apache/Perl)

slice array

non-sequential

# initialize @array with 10 elements,

# with values 1 through 10

@array = (1..10) ;

 

# @NewArray is a subset of @array

# (Note that @array is preceded by '@' here.

# We have to do that, since we're accessing

# several array elements at once.)

 

@NewArray = @array[3,6,9] ;

 

# Now, let's print the result

print join(" ", @NewArray) ;

 

OUTPUT:

4 7 10

sequential

# initialize @array with 10 elements,

# with values 1 through 10

@array = (1..10) ;

 

@AnotherNewArray = @array[3..6] ;

print join(" ", @AnotherNewArray) ;

 

OUTPUT:

4 5 6 7

from the end instead of from the beginning

# initialize @array with 10 elements,

# with values 1 through 10

@array = (1..10) ;

 

# print the last element in the array

print $array[-1] ;

 

OUTPUT:

10

sort array of arrays – see array or arrays, sort

split, opposite of – join

subroutine

sub mysubroutine
{
  print "Not a very interesting routine\n";
  print "This does the same thing every time\n";
}

regardless of any parameters that we may want to pass to it. All of the following will work to call this subroutine. Notice that a subroutine is called with an & character in front of the name:

&mysubroutine;         # Call the subroutine
&mysubroutine($_);     # Call it with a parameter
&mysubroutine(1+2, $_);       # Call it with two parameters
 
sub printfirsttwo
{
  print "Your first argument was $_[0]\n";
  print "and $_[1] was your second\n";
}

 

substring - $portion = substr($string, start number, length);

syntax

type in "perldoc [command]" as in "perldoc perl"

perldoc perlsyn - perl syntax

perldoc perlsub - perl subroutines

perldoc perlfunc - perl built-in functions -- ALL the functions - very tedious but seems to be complete

—T—

tab - \t

template, fill HTML

timestamp

use POSIX;

my $datestamp = strftime("%r %m/%d/%Y", localtime);

or

timestamp of existing file – see file time stamp

time

#!/usr/bin/perl -w

my $now = time();

($sec, $min, $hour, $mday, $Month, $year, $wday, $yday, $isdst) = localtime ($now);

print "seconds = $sec\n";

print "Minutes after each hour (0 - 59) = $min\n";

print "Hour since midnight (0 - 23) = $hour\n";

print "Numeric day of the month (1 - 31) = $mday\n";

#print "Number of months since January (0 - 11) = $Month\n";

# increment the month by 1 to get real month

my $RealMonth = $Month + 1; # Months of the year are not zero-based

print "Real Month = $RealMonth\n";

#print "year (Number of years since 1900) = $year\n";

# adding 1900 will create a four digit year value in your Perl script

$yyyy = $year + 1900;

print "year = $yyyy\n";

print "weekday (Number of days since Sunday (0 - 6)) = $wday\n";

print "Number of days since January 1 (0 - 365) = $yday\n";

print "A flag for daylight savings time = $isdst\n";

Tutorials

Wetware

manual

—U—

UnixDate

—V—

—W—

web page that called this script - see page that called this script

while loop, break out of – see loop, break out of

—X—

—Y—

—Z—

—No's—