At first, let me show you the source codes.
1) Base class
First question: Odd enough, I can not find the implementation of subroutine ‘can()’ anywhere. The command I used to find it:
The ‘.’ in the cmd above is the top level of the whole test suite.
Below is a child class:
Yet, another child class:
Second question: I know the implementions for both Sys::Stat::IO..xyz() and Switch..abc() are in the red part in Core::Accessor..make_accessor(). But I can not understand how xyz() is different from abc()? Or should abc() be different from xyz()? If they are different, then what the difference is?
Also, another question is embedded in the source code of the base class.
I am new to OOP in perl and I hope I have made myself clear. Thank you so much for your help.
1) Base class
Code:
package Core::Accessor;
sub new {
my $class = shift;
my $self = bless {}, ref $class || $class;
if ( $self->[b]can[/b]( 'init' ) ) {
[COLOR=blue]# can not find the implementation of subtorutine 'can()'[/color]
if ( ! $self->init( @_ ) ) {
undef( $self );
}
}
return $self;
}
[b][COLOR=red]sub register_fields {[/color][/b]
my ( $self, @fields ) = @_;
foreach my $field ( @fields ) {
if ( ! $self->[b]can[/b]( $field ) ) {
$self->make_accessor( $field );
}
$self->$field( undef );
}
}
sub make_accessor {
my ( $self, $field ) = @_;
my $class = ref( $self );
no strict 'refs';
[COLOR=blue][b] # Question: Could someone please explain what '*{ "${class}::${field}" }' is,
# especially, the leading '*'?[/b][/color]
[COLOR=red][b]*{ "${class}::${field}" }[/b] = sub {
my ( $self, $value ) = @_;
@_ > 2 and die 'Wrong usage!';
my $attr = $self->attr_name( $field );
my $type = ref( $self->{ $attr } );
if ( @_ == 1 ) {
return $self->{ $attr };
}
else {
return $self->{ $attr } = $value;
}
};[/color]
}
sub attr_name {
my ( $self, $field ) = @_;
return $self->PREFIX() . $field;
}
sub PREFIX { '_' };
1;
First question: Odd enough, I can not find the implementation of subroutine ‘can()’ anywhere. The command I used to find it:
Code:
% find . –name \* | xargs grep ‘sub can’
The ‘.’ in the cmd above is the top level of the whole test suite.
Below is a child class:
Code:
package Switch;
use strict;
use base qw(Core::Accessor);
# This child class has its own constructor
sub new {
my $proto = shift;
my $hash = shift; # startup hash
my $class = ref($proto) || $proto;
my $self = {};
bless ($self, $class);
$self->init($hash);
return $self;
}
sub init {
my $self = shift;
my $hash = shift;
# some implementations here
[COLOR=red]$self->[b]register_fields('abc')[/b][/color];
# some implementations here
}
sub check_abc {
my $self = shift;
my $deadpaths = shift;
# some implementations here
[b][COLOR=red]$self->abc($var);[/color][/b]
# some implementations here
}
1;
Yet, another child class:
Code:
package Sys::Stat::IO;
use base qw( Core::Accessor );
# This child class will use the constructor in base class
sub init {
my $self = shift;
# some implementations here
[b][COLOR=red]$self->register_fields('xyz');[/color][/b]
# some implementations here
}
sub get_xyz {
my $self = shift;
# some implementations here
[b][COLOR=red]return $self->xyz();[/color][/b]
}
1;
Second question: I know the implementions for both Sys::Stat::IO..xyz() and Switch..abc() are in the red part in Core::Accessor..make_accessor(). But I can not understand how xyz() is different from abc()? Or should abc() be different from xyz()? If they are different, then what the difference is?
Also, another question is embedded in the source code of the base class.
I am new to OOP in perl and I hope I have made myself clear. Thank you so much for your help.