kenics.net

Technical notes on perl, python, php, sql, cgi, c/c++, q/kdb+, unix/shell, revision control tools, data structures & algorithms, and their applications into web services and other various forms of software engineering.

perl general notes (data structures, regex, etc)

 
############################## 
####    perl  scripting    ### 
############################## 
 
#!/usr/bin/perl -w        # warns undef, unused vars, 100+ loops, etc 
use strict;               # only spell checks, syntax errors 
 
 
Characters 
---------------------------------------------- 
\U      convert all chars to upper case 
\u      convert the next char to upper case 
\L      convert all chars to lower case 
\l      convert the next char to lower case 
\r      carriage return 
\t      tab 
\n      new line 
\f      format the string 
\e      escape the next char 
\b      backspace 
 
 
######################### 
###   here document   ### 
######################### 
-------------------------- 
 #!/usr/bin/perl -w 
 
 $text = "Text from a Perl string."; 
 print <<HTML_HEREDOC;                  ## or <<"HTML_HEREDOC"    if you <<'HTML_HEREDOC'  then no variable expansion 
 <html> 
 <head> 
 <title>here document example</title> 
 </head> 
 <h1>here document example</h1> 
 <p>$text</p> 
 </body> 
 HTML_HEREDOC 
-------------------------- 
 
################################# 
####    special variables    #### 
################################# 
 
(ref) http://www.perlmonks.org/?node_id=353259 
 
$_    : default implicit var 
@_    : subroutine input args 
@ARGV : cmd line input args 
$|    : autoflush flag 1=true, 0=false. 
 
e.g. 
$ cmdLineArg.pl foo bar ken 
 
-----------------------------// cmdLineArg.pl 
 
$num_of_args = scalar(@ARGV);  # 3 
 
print $0;           # cmdLineArg.pl 
print $ARVG[0];     # foo 
print $ARVG[1];     # bar 
 
foreach $i (@ARGV){ 
    print $i,"\n"; 

 
----------------------------- 
 
aside: there are all sorts of special variables. 
e.g. $[ denotes the first index of all arrays. it is zero by default, but you can set it to any integer, then the first index of any array onward becomes that integer. 
 
 
####################### 
###   comment out   ### 
####################### 
 
# this line is commented out. use hash "#" char. 
 
=comment     # or =pod  # pod = plain old doc. 
 
these lines are 
commented out. 
use pod and cut 
 
=cut 
 
 
################################## 
###    comparison operators    ### 
################################## 
 
distinguish between numeric and string data types. 
 
 
numeric  |   string 
-------------------- 
  ==     |   eq 
  !=     |   ne 
  >      |   gt 
  >=     |   ge 
  <      |   lt 
  <=     |   le 
 
 
if("foo" == 0){    # this is true because string in numerical context resolves to zero 
    print "hit"; 

 
if("foo" == "var"){    # this is true as 0 == 0 
    print "hit"; 

 
if( 123 eq 123 ){      # resolves true 
    print "hit"; 

 
====> then why ever use "==" ?  because eq is an expensive ops. think in terms of C. 
 
 
@arr = ("_","*","=","-","&","@","Bb","bB","c","A","a"); 
print sort @arr;    #   prints &*-=@ABb_abBc 
 
====>  basically all \W first, then upper case char, "_" then lower case. 
====>  "a" is bigger than "A" 
 
 
 
################## 
###   false    ### 
################## 
 
the following are all false. 
 
if(0) 
if("0") 
if("") 
if(undef) 
if(defined($var))   # not defined 
 
################################### 
###   defined()  VS   exists()  ### 
################################### 
 
defined() returns false only for "undef" i.e. it will return 1 for "", 0, or anything defined. 
 
e.g. 
if(not defined $hash{$key}){print "key not in the table";} 
if(defined ($var = &func()) ){ do_something_here();} 
 
 
exists() checks if it's been decalared/initialized. 
 
## 
##  difference between defiend() and exists() 
## 
 
defined($hash{$key});   # to return 1, $key has to be registered in %hash, AND it has to be non 'undef' 
exists($hash($key));    # to return 1, $key has to be registered in %hash, and it can be any value including 'undef' 
 
http://stackoverflow.com/questions/6534573/whats-the-difference-between-exists-and-defined 
 
 
########################### 
####    outer loop     #### 
########################### 
 
last() alone only breaks out the immediate loop. 
 
FOO: while(1){ 
    BAR: while(1){ 
        while(1){ 
            last FOO;   # can specify which outer loop to break out of. 
            . 
            . 
 
 
################################# 
###   data types/structures   ### 
################################# 
 
scalar  # string or number or reference. e.g. int, str, double 
list    # read-only. not modifiable. (to be strict, list in perl is NOT a data structure, it's just a transient structure. 
array   # in-mem. random access. modifiable. 
hash    # aka dict in python, just a key-value map structure 
 
 
################## 
###   scalar   ### 
################## 
 
$var = 0; 
$var = 0.3; 
$var = "foobar"; 
$var = [123,456,789]; 
$var = {name => "ken", age => 27}; 
$var = sub {print 777;} 
 
 
 
################## 
####   array   ### 
################## 
 
@arr = ('a', 'b', 'c', 'd');  # notice ('a','b','c','d') is a list. 
@arr = qw {a b c d};          # same as above 
@arr = ['a', 'b', 'c', 'd'];  # [] creates a scalar, not an array, thus $arr[0][2] == c 
@arr = (11..15); 
@arr = (a..z); 
 
print @arr;         # abcd 
print "@arr";       # a b c d   (extra space in between) 
 
print $#arr;        # last index number of the array 
print scalar(@arr)  # number of contents 
$len = @arr;        # number of contents 
 
$#arr = 7;          # this will resize @arr to size 8. 
 
$num = (11,22,33,44,55);    #  same as  $num = 55; 
 
print scalar(reverse($line)),"\n"; 
 
@arr = split('/',$directory_path); 
@arr = split(//,$str);              # char array 
 
@date_info = ( localtime() )[3,4,5]; 
 
$arr[-1]    # last element 
$arr[-2]    # second last element 
 
 
## 
##  slice 
## 
 
@arr = (2,1,3,6); 
 
# slice an array (notice the syntax subtlety) 
print @arr[0,1,2];   # 2 1 3 
print @arr[0,3];     # 2 3 
print @arr[0,0];     # 2 2 
print @arr[0...2];   # 2 1 3 
print @arr[0...0];   # 2 
 
#### 
####   split() 
#### 
 
split(/pattern/,arg_string)  ## returns array after splitting the arg_string with pattern which is reg ex. 
 
$sentence = "I am a   cat."; 
@word = split(/\s+/,$sentence); 
 
-----------------------------//splitExample.pl 
$str = 'hello world   foobar'; 
@output0 = split(/\s/,$str); 
@output1 = split(/\s+/,$str);  # an example of regex delimeter 
 
foreach $i (@output0){     # this will print two empty lines between "world" and "foobar" 
    print $i,"\n"; 

 
foreach $i (@output1){     # this will print only non-whitespace three lines 
    print $i,"\n"; 

------------------------------ 
NOTE: split("",$str) yields char array 
 
 
## 
##  push @arr,LIST    # eseentially "append" 
## 
 
@arr = (2,1,3); 
$elem = 4; 
@arr2 = (5,6,7); 
 
push(@arr,$elem); 
print @arr;        #  2 1 3 4 
 
push(@arr,@arr2); 
print @arr;        #  2 1 3 4 5 6 7 
 
 
## 
##  pop @arr    # removes & returns the last elem of @arr 
## 
 
@arr = (1,2,3,4); 
print pop(@arr);   #  4 
print @arr;        #  1 2 3 
 
 
## 
##  shift @arr    # removes & returns the first elem of @arr 
## 
 
@arr = (1,2,3,4); 
print shift(@arr);   #  1 
print @arr;          #  2 3 4 
 
 
## 
##  unshift @arr,LIST    # essentially "prepend" 
## 
 
@arr = (2,1,3); 
$elem = 4; 
@arr2 = (5,6,7); 
 
unshift(@arr,$elem); 
print @arr;          #  4 2 1 3 
 
unshift(@arr,@arr2); 
print @arr;          #  5 6 7 4 2 1 3 
 
 
## 
##  splice   (not to be confused with slice) 
## 
(ref) 
http://perldoc.perl.org/functions/splice.html 
 
 
 
 
 
######################### 
#####     hash      ##### 
######################### 
 
a hash is a collection of key-value pairs. 
 
---------------------------- hash_usage.pl 
#!/usr/bin/perl 
 
%h = (foo => 123, bar => 456, baz => 789 ); 
%h = qw(foo 123 bar 456 baz 789);            # same as above 
 
foreach $i (sort( values(%h) ))     ## prints hash values sorted 

   print $i."\n"; 

 
foreach $i (sort( keys(%h) )) 

    print $i.":".$h{$i}."\n"; 

----------------------------- 
 
 
#### 
####  how is hash implemented in Perl ? 
#### 
 
it is a plain good old hash structure where a hash function converts an input key into an array index. For collision resolution, the separate chaining method is used (as opposed to the open addressing method). 
(Perl hash src code) 
http://cpansearch.perl.org/src/NWCLARK/perl-5.8.8/hv.c 
(Perl hash func src code) 
http://cpansearch.perl.org/src/DOM/perl-5.12.5/hv.h 
 
 
As above, Perl's hash function is simply taking the input key as string and adding all bits up (plus lots of bit shifting up & down with additon and xor, which supposedly leads to the uniform distribution of the output...) 
 
register const char * const s_PeRlHaSh_tmp = str; 
 register const unsigned char *s_PeRlHaSh = (const unsigned char *)s_PeRlHaSh_tmp; 
  register I32 i_PeRlHaSh = len; 
   register U32 hash_PeRlHaSh = PL_rehash_seed; 
while (i_PeRlHaSh--) { 
            hash_PeRlHaSh += *s_PeRlHaSh++; 
            hash_PeRlHaSh += (hash_PeRlHaSh << 10); 
            hash_PeRlHaSh ^= (hash_PeRlHaSh >> 6); 
         } 
         hash_PeRlHaSh += (hash_PeRlHaSh << 3); 
 hash_PeRlHaSh ^= (hash_PeRlHaSh >> 11); 
  (hash) = (hash_PeRlHaSh + (hash_PeRlHaSh << 15)); 
 
 
## aside: perl's internal hash function used to be simpler as below. 
 
unsigned int hash = 0; 
while (*s)  /* s is pointer to string */ 
    hash = hash * 33 + *s++; 
return hash; 
 
(ref) http://www.perlmonks.org/bare/?node_id=917221 
 
 
##### 
#####  hash of hash 
##### 
 
multi-dimensional is possible. 
 
e.g. 
-------------------------------- 
 
%HoH = (                             ## defining a nested hash of hash (HoH) 
     flintstones => { 
         husband     => "fred", 
         pal         => "barney", 
     }, 
     jetsons => { 
         husband     => "barry", 
         wife        => "jane", 
         "first boy" => "elroy",     ## if key is more than two words, "" double quotes needed. 
     }, 
     simpsons => { 
         husband     => "homer", 
         wife        => "marge", 
         kid         => "bart", 
     } 
); 
 
 
$HoH(mash) = { 
   captain  => "pierce", 
   major    => "burns", 
   corporal => "radar", 
}; 
 
 
###  printing 
 
for $family ( keys %HoH ) { 
    print "$family: "; 
    for $role ( keys %{ $HoH{$family}} ) 
    { 
        print "$role = $HoH{$family}{$role}"; 
    } 
    print "\n"; 

 
---------------------------------- 
 
 
 
####### 
#######  exchange keys and values 
####### 
 
------------------------------- 
 
%h = qw (morgan stanley goldman sachs lehman brothers); 
%rh = (); 
 
foreach $key (keys %h) 

   $rh{$h{$key}} = $key; 

 
foreach $k (keys %rh) 

   print $k." ".$rh{$k}."\n"; 

-------------------------------- 
 
 
###### 
######  identifying dupe values in hash 
###### 
 
------------------------------- 
 
%th = qw (morgan stanley goldman sachs lehman brothers fake stanley); 
@uniq = grep { $h{$_}++ } values %th; 
print "@uniq"."\n"; 
 
------------------------------- 
 
 
################################### 
#####    built-in functions    #### 
################################### 
 
see a complete list here (ref) http://perldoc.perl.org/perlfunc.html 
but here are freq used ones. there are ones for maniulating scalar, or array, or numerical ops, time, fileio, etc. 
 
 
chop ($str);     # removes a char at the end 
chomp($str);     # removes any newline at the end 
                 # to be exact, remove any trailing string that matches a special var $/ which is a newline by default 
 
---------------------//chomp.pl 
 
print ord($/);       # print 10 which is "\n" in ascii 
 
$str = "hello\n\n\n"; 
chomp $str;          # removes only the last "\n" 
 
chomp $a,$b;         # this becomes chomp($a),$b 
chomp ($a,$b);       # proper 
print (@arr);        # chomp on each elem 
--------------------- 
 
 
length ($str)    # returns the number of characters in a string 
                 # canNOT use on array 
                 # to know the number of elem in array/hash, write   scalar @arr   and   scalar keys %hash 
 
---------------------//length.pl 
$text = "hello"; 
@arr = split(//,$text); 
$len = $#arr + 1;         effectively the same as  length($text) 
--------------------- 
 
 
 
### 
###   sort (@arr);   # sorts elements 
### 
---------------------------------// sort.pl 
 
#!/usr/bin/perl 
 
%stocks=qw(foo 10 bar 40 cmu 33 ken 123); 
 
@sortedArr = sort (keys(%stocks));              # sort keys alphabetically by default 
@sortedArr = sort keys %stocks;                 # same as above 
@sortedArr = sort { $a cmp $b } keys %stocks;   # same as default   a,b,c,,,,z 
@sortedArr = sort { $b cmp $a } keys %stocks;   # descending order  z,y,x,,,,a 
                                                # use "cmp" for string 
 
## NOTE:  yes, $a and $b are special variables. 
 
# sort keys by values 
@sortedArr = sort {$stocks{$a} <=> $stocks{$b}} (keys(%stocks));   # use <=> for numerical comparison 
                                                                   # swap $a $b for descending order 
print @sortedArr;       #foo cmu bar ken 
 
# print values by sorted keys 
foreach $i (sort keys %stocks){ 
    print $stocks{$i}; 
    print "\n"; 

 
@arr = ("foo","bar","ken","f","bb","b","k"); 
# sort by length first, then by alphabetical 
@sortedArr = sort { length $b <=> length $a || $a cmp $b } @arr;   #  bar foo ken bb b f k 
 
----------------------------------- 
 
 
 
#### 
####   qw() 
#### 
 
@arr = ("foo", "bar", "mel");   ##  qw makes it easier. 
@arr = qw( foo bar mel );       ##  parenthesis is just a delimeter.  space at each end is important. 
                                ##  can be qw{ foo bar mel }  qw[ foo bar mel ]   qw/ foo bar mel / 
 
 
#### 
####  rand() 
#### 
 
$val = rand();    ## gives a float val between 0 to 1   e.g.  0.784091423 
$val = rand(100); ## gives a float val between 0 to 100 e.g.  83.4237891 
$val = int(rand(100));  ## to make it int 
 
 
#### 
####   localtime() 
#### 
 
my ($sec, $min, $hour, $day, $mon, $year) = localtime(time); 
$timestamp=sprintf('%04d%02d%02d.%02d%02d%02d', $year + 1900, $mon + 1, $day, $hour, $min, $sec); 
 
print $timestamp;  ## shows  YYYYMMDD.HHMMSS   #sprintf enables how many digits to explicitly display 
 
 
### 
###  sprintf() 
### 
 
my $twoDecimal = sprintf("%.2f",12.345678);    # 12.35 
 
 
### 
###  glob() 
### 
 
my @file_list = glob("/tmp/data/20170[123]??.csv");   # you can use regex like this 
 
 
#### 
####   index($str,$substr,$position) 
#### 
--------------------------// index.pl 
#!/usr/bin/perl 
 
$str = "abcdc"; 
print index($str,'c');   # 2 
print index($str,'c',2); # 2 
print index($str,'c',3); # 4 
print index($str,'x');   # -1 
-------------------------- 
 
 
### 
###  uc() lc() tr() 
### 
 
upper case, lower case, flip 
 
print uc("AbcD");     #  ABCD 
print lc("aBCd");     #  abcd 
 
my $str = "AbcD"; 
$str =~ tr[A-Za-z][a-zA-Z]; 
print $str;                  #  aBCd 
 
 
### 
###   int() 
### 
 
print int(3.14);  # 3 
 
 
### 
###   ord()  chr() 
### 
 
ord() == atoi() 
chr() == itoa() 
 
print ord('a');   #  97 
print ord("abc"); #  97      notice how only the first char is referred to. 
 
print chr(97);    #  'a' 
 
 
### 
###   join(<delim>,<array>) 
### 
 
@arr = ('aaa','bbb','ccc'); 
$str = join( ',' , @arr ); 
print $str;                     # aaa,bbb,ccc 
 
 
### 
###   umask(expr) 
### 
 
just like unix cmd, sets the mask for permission bits. 
note it is a mask, not the actual chmod. 
 
umask 077;  # makes chmod 700 whatever created thereafter. 
umask;      # returns current mask 
 
 
### 
###  unlink/symlink   # sometimes perl version dependent, so make sure you test in your env 
### 
 
symlink(actual_filename,symlink_name);  # suppose symlink_name is already defined, and you wanna overwrite 
unlink(symlink_name);                   # then you need to unlink first 
 
 
 
################################# 
####     random exercise     #### 
################################# 
 
 
##### 
#####  line/byte counter 
##### 
 
--------------------------- 
 
%bytes=(); 
$index=1; 
 
while(<>) 

    $input = $_; 
    chomp($input); 
    $bytes{$input} = length($input); 

 
foreach $k (keys %bytes) 

    print $index.": ".$k." size is ".$bytes{$k}."\n"; 
    $index++; 

 
----------------------------- 
 
 
##### 
#####  word size sum / avg. word size / frequency per size 
##### 
 
----------------------------- 
 
%size=(); 
 
while(<>) 

    chomp $_; 
    @line = split(//,$_); 
    $wnum = $wnum + $#line + 1; 
    @warr = split(/\s+/,$_); 
    $len = $len + $#warr + 1; 
 
  foreach(@warr) 
  { 
      $tmplen = length($_); 
      $size{$tmplen}++; 
  } 

 
print "size of all words: ".$wnum."\n"; 
print $len."\n"; 
print "average word size: ".($wnum/$len)."\n"; 
 
foreach $k (keys %size) 

    print $k." ".$size{$k}."\n";  ## word of size k occurred $size{$k} times 

 
 
----------------------------- 
 
 
#### 
####   spell checker 
#### 
--------------------------- 
 
#!/usr/bin/perl 
 
open(FH, "</usr/share/dict/words"); 
 
%dict = (); 
 
while(<FH>) 

    chomp $_; 
    $dict{$_} = 1; 
    #  print $_."\n" 

 
close FH; 
 
while(1) 

    $lines=<STDIN>; 
    chomp $lines; 
    @word = split(/ /,$lines); 
 
    foreach $i (@word) 
    { 
        if( $dict{$i}){ 
            print $i." is in the dictionary.\n"; 
        }else{ 
            print $i." is NOT in the dictionary.\n"; 
        } 
    } 

 
---------------------------- 
 
 
############################################# 
#####    regular expressions (regex)    ##### (ref) http://perldoc.perl.org/perlre.html 
############################################# 
 
 
\w    #  [a-zA-Z_] 
\W    #  [^a-zA-Z_] 
\d    #  [0-9] 
\D    #  [^0-9] 
\s    #  [whitespace,tab,newline] 
\S    #  not \s 
 
 
=~ is for match 
e.g. 
"hello world" =~ /world/;  # matches 
                           # to negate =~   use !~ 
 
m//  lets you change '/' to arbitrary delimeter 
e.g. 
"hello world" =~ m!world!; 
 
s///  is for replace 
e.g. 
$text = "hello world"; 
$text =~ s/world/foo/;   # hello foo 
$text =~ s/foo//;        # hello 
 
//<modifier>   # you can put modifier char 
 
 i     # case insensitive 
 g     # globally match 
 m     # multi lines 
 s     # single lines 
 x     # permits whitespace/comments 
and more... 
 
e.g. 
"hello world WORLD World" =~ s/World/foo/gi;   # this converts all 3 cases of world 
 
 
##### 
#####  regex exercise 
##### 
 
---------------------------// regex.pl 
 
$line1 = "abcABC"; 
$line2 = "abc2ABC3j"; 
$line3 = "123abc 645 abc"; 
 
if( $line1 =~ /^[a-zA-Z]+$/ ){   # checks if the line contains only letters 
    print $&,"\n"; 

 
if( $line2 =~ /^a-zA-Z/ ){       # checks if the line contains any non-letter and prints the first non letter 
    print $&,"\n"; 

 
$line3 =~ s/([a-zA-Z])//g;       # remove all alphabets 
print $line3;                    # print "123 456" 
 
$data = 123; 
%numbers = qw(1 one 2 two 3 three); 
$data =~ s/(\d)/$numbers{$1}/g;       # clever way to replace all numbers 
print $data;                          # "one two three" 
 
$line = "welcome to the towns";  # notice how we have two occurrences of "to" 
$line =~ s/.*to//;               # greedy match. matches till the final occurrence. 
print $line;                     # "wns" 
 
$line = "welcome to the towns"; 
$line =~ s/.*?to//;              # first match 
print $line;                     # " the towns" 
 
--------------------------- 
 
---------------------------------// group.pl 
#!/usr/bin/perl 
 
$line = "Hello buddy, is there any beer?"; 
 
if ( $line =~ /((\w+)\s+(\w+))\s+(\w+)/ )    # notice there are 4 groups 

    print $0."\n";    # group.pl   <script name> 
    print $1."\n";    # is there 
    print $2."\n";    # is 
    print $3."\n";    # there 
    print $4."\n";    # any 
    print $`."\n";    # hello buddy,       #   $` = "pre" 
    print $&."\n";    # is there any       #   $& = "match" 
    print "$'";       # beer               #   $' = "post" 

---------------------------------- 
 
----------------------------------// regex2.pl 
#!/usr/bin/perl 
 
$line = "Twinkle, twinkle, little star!"; 
@arr = split(/\W+/,$line);                 # split by [^a-zA-Z_] 
foreach $e (@arr){ 
        print $e; 
        print "\n"; 

--------------------------------- 
 
---------------------------------// first_match.pl 
#!/usr/bin/perl 
 
$line = "Do you like Peter Rabbit Jonie?"; 
if ( $line =~ /Pete|Peter|Jonie|Joan/ ) 

    print $&;       # Pete 

--------------------------------- 
 
 
############################## 
####   custom functions   #### 
############################## 
 
### 
###   trimmer 
### 
--------------------// trim.pl 
sub trimmer{ 
    my $str = shift; 
    $str =~ s/^\s+//g; 
    $str =~ s/\s+$//g; 
    return $str; 

## use with chomp($str); 
--------------------- 
 
### 
###  logprint 
### 
 
sub logprint { print scalar(localtime), "| @_";}     # prints timestamp 
 
 
 
 
########################### 
####   bespoke substr   ### 
########################### 
 

#  print my_substr("Tom & Jerry", 4, 1);   # should print "&" 
#  if there is no third arg, trim till the end of the string 

-------------------------------------------------// my_substr.pl 
 
#!/usr/bin/perl 
 
sub my_substr 

    @inarr = @_; 
    @arr = split(//,$inarr[0]); 
    $begin = $inarr[1]; 
    $end = 0; 
    @output = (); 
 
    if($#inarr == 1){ $end = $#arr + 1;} 
    elsif($#inarr == 2){ $end = $begin + $inarr[2]} 
    else{print "error";} 
 
    for ($i = $begin; $i < $end; $i++){ 
        push @output,$arr[$i]; 
    } 
    return @output; 

 
print my_substr("Tom & Jerry",4,3),"\n"; 
print my_substr("Tom & Jerry",4),"\n"; 
 
 
------------------------------------------------- 
 
 
########################################### 
######    compile/run time blocks     ##### 
########################################### 
 
(ref) 
http://stackoverflow.com/questions/3998619/what-is-the-role-of-the-begin-block-in-perl 
 
in short, the perl code runs in the below sequence. 
 
BEGIN{} 
CHECK{} 
INIT{} 
main code runs here 
END{} 
 
 
 
########################################## 
#######       module / package     ####### 
########################################## 
 
module file should be named .pm for convention and convenience as below. 
 
@INC  # a special variable equivalent to PATH env var in shell. PATH contains a list of directories to search for executables, @INC contains a list of directories from which Perl modules and libraries can be loaded. 
 
%INC  # a special var that contains the imported module and its absolute path. 
e.g. 
-------------------------------------------------------------------------------- 
%INC = ( 
         'warnings/register.pm' => 'C:/Perl/5.8.8.822/lib/warnings/register.pm', 
 
         'bytes.pm' => 'C:/Perl/5.8.8.822/lib/bytes.pm', 
         'XSLoader.pm' => 'C:/Perl/5.8.8.822/lib/XSLoader.pm', 
         'Carp.pm' => 'C:/Perl/5.8.8.822/lib/Carp.pm', 
         'Exporter.pm' => 'C:/Perl/5.8.8.822/lib/Exporter.pm', 
         'strict.pm' => 'C:/Perl/5.8.8.822/lib/strict.pm', 
         'warnings.pm' => 'C:/Perl/5.8.8.822/lib/warnings.pm', 
         'overload.pm' => 'C:/Perl/5.8.8.822/lib/overload.pm', 
         'Data/Dumper.pm' => 'C:/Perl/5.8.8.822/lib/Data/Dumper.pm' 
       ); 
--------------------------------------------------------------------------------- 
 
 
use() require() do() a module will search @INC and load the file. Otherwise specify the full path. 
the diff between use() and require/do() is use() exec imports at compile time, and require/do at run time. 
the diff between require() and do() is require() checks if the module is already loaded or not, and does not load again. (efficient) also require() does not need to specify the exact module name. 
 
(ref) 
http://d.hatena.ne.jp/perlcodesample/20090208/1232890021 
 
 
 
---------------------------------// ken.pm 
 
package ken;         # package <namespace>  declares the rest of the code as <namespace> (until another package is called.) 
use Exporter; 
@ISA = qw(Exporter); 
@EXPORT = qw(foo);     # this array stores the subroutines you wanna export from the module 
@EXPORT_OK = qw(bar);  # this array stores the subroutines only to be exported upon request 
 
sub foo{ 
        a::foo(@_);    # dont forget to pass in the @_ for the underlying subroutine 

sub bar{ 
        b::bar(@_); 

 
package a; 
 
sub foo{ 
        print "foo "; 
        print @_,"\n"; 

 
package b; 
 
sub bar{ 
        print "bar "; 
        print @_,"\n"; 

 
1;   # must end with true and a semi-colon 
 
 
--------------------------------- 
---------------------------------// main.pl 
 
#!/usr/bin/perl 
 
use lib "/hoge/hoge";  #  same as   BEGIN { unshift(@INC, "/hoge/hoge"); } 
 
use ken;     # use = BEGIN{require ken; import ken LIST;}  # loads func, var, export setting 
             # BEGIN forces the require/import at the compile time 
# or 
require ken; # does not import until the run time 
# or 
do "ken.pm"; 
 
foo("hello");    # "foo hello" 
bar("world");    # error because it is not exported. write    use ken qw(bar)   at the top 
 
---------------------------------- 
 
 
@ISA  # each package has its own @ISA array which keeps track of inherited classes. 
 
e.g. 
------------------------------------------- 
package Abc; 
sub foo{do_something;} 
 
package Xyz; 
@Xyz::ISA = qw(Abc); 
sub bar{do_something;} 
 
Xyz->foo;   # this will resolve to Abc::foo 
------------------------------------------- 
 
 
 
##################################### 
#####    reference and object    #### 
##################################### 
 
OOP in perl is tricky. done via reference. (normally one shall use c++,java,python,etc for OOP) 
 
 
------------------------------------// ref.pl 
 
#!/usr/bin/perl 
 

# referencing 

 
$sca_ref  = \$var; 
 
$arr_ref  = \@arr; 
$arr_ref  = [123,456,789];   # implicit 
 
$hash_ref = \%hash; 
$hash_ref = {name => "ken", age => 23};  # implicit 
 
$sub_ref = \&some_sub; 
$sub_ref = sub{print "halo world";}  # implicit 
 
 
print $sca_ref;     # this prints smth like SCALAR(0x80fea8c) 
 
 

# dereferencing (a few diff ways to deref) 

 
print $$sca_ref; 
print ${$sca_ref}; 
 
print @$arr_ref; 
print @{$arr_ref}; 
print ${$arr_ref}[3]; 
print $arr_ref->[3];  # same as above 
 
print %$hash_ref; 
print %{$hash_ref}; 
print ${$hash_ref}{name}; 
print $hash_ref->{name};  # same as above 
 
print &$sub_ref(); 
print &{$sub_ref}(); 
 
 

#  examples 

 
@arr = ([1,2,3],[4,5,6],[7,8,9]);  # a regular two dimensional array 
print $arr[2][2];                  # notice the single dollar sign 
                                   # prints 9 
                                   # you can alternatively write as $arr[2]->[2] 
 
$parr = [[1,2,3],[4,5,6],[7,8,9]]; # now declare a reference to it 
print $$parr[2][2];                # notice the double dollar sign 
                                   # prints 9 
 
%h = ('a' => {'b' => 2,'c' => 3}, 'd' => {'e' => 4, 'f' => 5}); 
$h_ref = \%h;               # a ref to a hash 
print $h{'a'}{'b'};         # 2 
print $h_ref->{'a'}{'b'};   # 2 
 
------------------------------------- 
 
(ref) 
http://perldoc.perl.org/perlreftut.html 
http://perlmeme.org/howtos/using_perl/dereferencing.html 
 
 
#### 
####  passing arrays/scalars by ref into a subroutine prevents them from getting combined. 
#### 
e.g. 
someFunc(@arr0,@arr1);  #  these two input arrays get combined when accessed @_ within sub someFunc{} 
 
in general, there are two ways to get around this problem. 
(1) pass by reference 
(2) prototype 
 
-------------------------------------// ref_vs_proto.pl 
 
#!/usr/bin/perl 
 
sub printInputs{ 
    $x = $_[0];       # normal input arg use 
    $y = $_[1]; 
    print $x,"\n"; 
    print $y,"\n"; 

 
sub passByRef{          # takes two arrays and a scalar by reference 
    @arr0 = @{$_[0]};   # here is how you extract the 1st array 
    @arr1 = @{$_[1]};   # second array 
    $scr = ${$_[2]};    # then the scalar 
 
    print @arr0,"\n"; 
    print @arr1,"\n"; 
    print $scr,"\n"; 

 
sub proto(\@\@\$){       # see the explicit prototype declaration 
    @arr0 = @{$_[0]};    # the rest of the subroutine definition is the same 
    @arr1 = @{$_[1]};    # BUT notice when invoked, no longer need to pass by ref 
    $scr = ${$_[2]}; 
 
    print @arr0,"\n"; 
    print @arr1,"\n"; 
    print $scr,"\n"; 

 
 
@arrA = ('a','b','c','d','e'); 
@arrB = ('f','g','h','i','j'); 
$char = 'k'; 
 
printInputs(2,4); 
passByRef(\@arrA,\@arrB,\$char); 
proto(@arrA,@arrB,$char);         # proto way lets user use the subroutine like build-in func. 
 
 
------------------------------------- 
 
 
#### 
####  ref() 
#### 
 
a built in func that identifies what data type a ref points to. 
 
----------------------------// ref.pl 
 
#!/usr/bin/perl 
 
$sca_ref  = \$var; 
$arr_ref  = \@arr; 
$hash_ref = \%hash; 
$sub_ref  = \&some_sub; 
 
print ref $sca_ref;   #  SCALAR 
print ref $arr_ref;   #  ARRAY 
print ref $hash_ref;  #  HASH 
print ref $sub_ref;   #  CODE 
 
---------------------------- 
 
 
 
############################# 
###   CPAN and friends    ### 
############################# 
 
## 
##  sending email with an attachment 
## 
 
http://search.cpan.org/~yves/MIME-Lite/lib/MIME/Lite.pm 
 
$  cat   sampleEmail.pl 
#!/usr/bin/perl 
use MIME:Lite; 
 
my $msg = MIME::Lite->new( 
    To      => 'foo@bar.com, kenics@sample.com', 
    CC      => 'someone@abc.com', 
    Subject => 'this is email subject', 
    Type    => 'multipart/related' 
   ); 
$msg->attach( 
   Type  => 'text/html', 
   Data  => qq{ 
   <body> 
   here is a test image: <img src="cid:foobar.jpg"> 
   </body> 
   }, 
   ); 
$msg->attach( 
   Type => 'image/jpeg', 
   Id   => 'foobar.jpg', 
   Path => '/path/to/foobar.jpg', 
   Disposition => 'attachment',        # default is 'inline' but you can choose to make it 'attachment' 
   );                                  # you can duplicate this chunk to send image both as attachment and as inline image 
$msg->send(); 
 
exit 0; 
 
 
 
 

  1. 2013-11-25 00:57:06 |
  2. Category : perl
  3. Page View:

Google Ads