- 论坛徽章:
- 0
|
1、说明
本程序演示了在Perl中如何进行面向对象编程:演示程序包含两个文件:person.pl 和 person.pm,把 person.pl 和 person.pm 放在当前目录下,运行"perl person.pl"即可以看到结果。person.pm定义了名为person的类。person.pl中创建了person类的实例,并测试了person的成员方法。
2、person.pm的内容
- #!/usr/bin/perl -w
- package person;
- use strict;
- 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) = @_;
- $self->{"name"} = $name;
- }
- sub getSex {
- my ($self) = @_;
- return $self->{"sex"};
- }
- sub setSex {
- my ($self, $sex) = @_;
- $self->{"sex"} = $sex;
- }
- 1;
复制代码
注意new方法中的最后一行:我发现去掉这条语句程序还是可以正常运行,有谁知道为什么?
3、person.pl的内容
- #!/usr/bin/perl -w
- use strict;
- use person;
- sub main()
- {
- my $tom = person->new("Tom", "male");
- my $kiss = person->new("Kiss", "female");
- my @persons = ($tom, $kiss);
- for my $p (@persons) {
- printf("NAME: %s\tSEX: %s\n", $p->getName(), $p->getSex());
- }
- }
- &main();
复制代码
4、程序运行结果
CLASS = person
CLASS = person
NAME: Tom SEX: male
NAME: Kiss SEX: female
5、当调用person->new("Tom", "male")时发生了哪些事情?
下面我们将重点分析下面的代码,为了查看方便,我把它粘贴过来了:
- sub new {
- my $class = shift();
- print("CLASS = $class\n");
- my $self = {};
- $self->{"name"} = shift();
- $self->{"sex"} = shift();
- bless $self, $class;
- return $self;
- }
复制代码
- 当调用person->new("Tom", "male")时,有3个参数被传递给person中的new函数,它们分别是: 类的名称"person"(这是一个隐含参数)、"Tom"、"male"。
- 语句my $class = shift();获得第一个参数
- 语句my $self = {};创建一个哈希表对象的引用
- 语句$self->{"name"} = shift(); 把传进来的第二个参数存入到哈希表中。
- 语句$self->{"sex"} = shift(); 把传进来的第三个参数存入到哈希表中。
- 语句bless $self, $class,我把bless理解为"把类型信息和变量绑定" :
- $self是一个指针,在这里指向了一个哈希表对象的引用
- $class是一个字符串,在这里是person类的名字
- 在perl中,根据类的名字可以查找到这个类所有的成员方法和成员变量,因此类的名称就代表了类的类型信息!
- 所谓bless就是把 person类的类型信息 赋予 哈希表对象的引用
- 语句return $self;则返回哈希表对象的引用
这里我有两个问题:- 为什么我把person->new()中最后一条return $self;语句去掉后,程序仍然可以正确运行了?
- person.pm中的最后一条语句1;不可以遗漏,否则在person.pl中加载person.pm模块失败,我的理解是在perl.pl中use person时,会去尝试执行person.pm脚本,根据返回值判断初始化是否成功。
6、后记
通过一段时间的摸索,我已经基本熟悉了perl的面向过程编程,我打算学习perl的OO编程和引用的概念,这是我编写的第一个perl OO程序,原先我以为编写一个Person类是非常容易的,后来发现编写一个最简单的OO程序还是挺麻烦的,这里要感谢zhang1120,他编写的MyCGI模块有很大的参考价值。
在编写过程中,我主要遇到了如下的困难,给初学者参考:- 网上的参考资料质量太差而且排版差,要找一个简单的、完整的例子都不容易。
- 理解bless的概念。bless关键字的名称非常不直观,"把类型信息和变量绑定" 与 "祝福" 有什么联系?如果把bless改为bind,就不用初学者那么费劲的去猜bless的含义了。
- 在person.pm的末尾要加上1;, 不加这条语句的话,use person会失败。
[ 本帖最后由 DennisRitchie 于 2007-8-24 02:40 编辑 ] |
|