1.Shell中命令执行结果或者文件内容会自动将换行符或者单个多个空格转化为单空格赋值给变量$
,而在perl中命令执行结果和文件内容会以行为单位(包括\n)赋值给数组变量@
中各元素,对于一般变量$
命令执行结果会整体赋值给变量,而文件句柄则会以行为单位依次赋值给变量,因此perl可以保存原始文本的格式。
2.Program = Data Structure + Logical + operator/function/command
,shell中存在数组变量但应用较少,但平台下的常用指令均可应用在shell中,因此shell功能依旧很强大,perl中数据结构有列表()
、变量$
、数组@
、哈希%
、函数&
以及众多操作符和内置外置函数。
perl 面向对象机制:
1.perl的引用即是指针,因此perl中都是值传递。
2.perl中所谓的类即是包名,也就是包/模块的字符串,而所谓的方法即是包/模块中定义的函数,使用->
方式调用函数后隐形传递函数模块名作为第一个参数,而是用::
方式调用则无隐形传递,隐形传递模块名实现模块内定义的函数能获取到模块名进而进行方法调用,是perl实现伪面向对象特性重要设计。
$class = |package_name|
$class->|sub|
|package_name|->|sub|
3.不同于模块中的函数,模块中定义的变量只能通过::
实现访问,因此为了实现意义上的类或者对象 数据和方法 的联合(表面上即均通过->
符号调用,不同的是->
调用的方法是模块中定义的函数,->
调用的数据是指针指向的内存块)perl引入了bless操作符。
3.bless用于将一个引用变量(指针变量)关联到一个类即模块名上(区别于引用的全新数据格式,一般为|class|=HASH<0x12345>
),bless $ref |package_name|
或者 bless $ref $class
, 这样$ref
即可通过->
调用引用的数据又可通过->
调用模块中的方法,这也是perl实现伪类方法(即模块函数)和对应数据关联的关键设计。
参考程序:
person.pm
#!/usr/bin/perl
package person;
sub new {
my $class = shift;
print "Class = $class \n";
my $self = {};
$self->{'name'} = shift;
$self->{'sex'} = shift;
bless $self,$class;
return $self;
}
sub getname {
my ($self) = @_;
return $self->{'name'};
}
sub setname {
my ($self,$name) = @_;
return $self->{'name'} = $name;
}
sub getsex {
my ($self) = @_;
return $self->{'sex'};
}
sub setsex {
my ($self,$sex) = @_;
$self->{'sex'} = $sex;
}
sub echo {
print "placeholder\n";
}
1;
person.pl
#!/usr/bin/perl -w
use lib '/home/bruce/lib';
use person;
use ejng::zhang;
sub main {
my $tom = person->new('tom','male');
my $lili = person->new('lili','female');
print $tom->getname,"\n";
print $lili->getname,"\n";
print $tom->getsex,"\n";
print $lili->getsex,"\n";
$tom->setname('tom_crush');
$lili->setname('lili_zhang');
print $tom->getname,"\n";
print $lili->getname,"\n";
}
&main;
4.实现在程序中直接使用模块中定义子例程名字调用方法有两种,均于perl自身import机制有关。
方法1:使用半底层的perl 符号hash将子例程的指针定义到main包里,缺点是必须在use 后使用import,否则不生效。
sub.pm
#!/usr/bin/perl
package sub;
sub import {
foreach (@_) {
*{"main::$_"} = \&$_;
}
}
sub echo {
print "Placeholder!\n";
}
1;
sub.pl
#!/usr/bin/perl
use sub qw/echo/;
echo;
方法2:使用perl官方的Exporter
模块。
sub.pm
#!/usr/bin/perl
package sub;
use Exporter;
our @EXPORT = qw/echo/;
our @ISA = qw(Exporter);
sub echo {
print "Placeholder!\n";
}
1;
sub.pl
#!/usr/bin/perl
use sub;
echo;
5.@ISA实现所谓类的继承机制。
Reference:https://my.oschina.net/OliverTwist/blog/225178