以下の方法では動かない。
package hoge;
sub new{
my $class=shift;
my $self={'msg2' => 'harahoro','hoge' => \&hoge};
bless $self,$class;
return $self;
}
sub fuga{
my $self=shift;
my $msg =shift;
my $classname=ref $self;
print "from $classname : hello! $msg\n";
}
sub hoge{
my $self=shift;
my $msg = shift;
print "I am calling fuga\n";
$self->fuga("hoge : $msg and ". $self->{"msg2"});
}
1;
package main;
my $moga=hoge->new;
$moga->{'hoge'}->('self hash');
当然、以下も動かない。
package hoge;
sub new{
my $class=shift;
my $self={'msg2' => 'harahoro'};
bless $self,$class;
$self->init;
return $self;
}
sub init{
my $self=shift;
$self->{"hoge"} = \&hoge;
}
sub fuga{
my $self=shift;
my $msg =shift;
my $classname=ref $self;
print "from $classname : hello! $msg\n";
}
sub hoge{
my $self=shift;
my $msg = shift;
print "I am calling fuga\n";
$self->fuga("hoge : $msg and ". $self->{"msg2"});
}
1;
package main;
my $moga=hoge->new;
$moga->{'hoge'}->('self hash');
以下の2点が問題
- $self->funcのリファレンス取得方法がない
- \&funcとするとinvocantが渡らない
なので、以下のような解決方法になる。
package hoge;
sub new{
my $class=shift;
my $self={'msg2' => 'harahoro'};
bless $self,$class;
$self->init;
return $self;
}
sub init{
my $self=shift;
$self->{"hoge"} = $self->hoge_invocant;
}
sub fuga{
my $self=shift;
my $msg =shift;
my $classname=ref $self;
print "from $classname : hello! $msg\n";
}
sub hoge_invocant{
my $invocant=shift;
return sub { hoge($invocant, @_);};
}
sub hoge{
my $self=shift;
my $msg = shift;
print "I am calling fuga\n";
$self->fuga("hoge : $msg and ". $self->{"msg2"});
}
1;
package main;
my $moga=hoge->new;
$moga->{'hoge'}->('self hash');
hoge_invocantが
「invocantをレキシカルクロージャとして保持しhogeをinvocantつきで呼び出す無名関数」
を返す。
ここで無名関数を使うべきだということに気付いた。
sub init{
my $self=shift;
$self->{"hoge"} = sub {hoge($self, @_);};
}
追記~~
<iframe id=”4873112036”src=”http://motivation.drivendevelopment.jp/amazon_query_proxy/queryproxy_ruby.cgi?ItemId=4873112036” onload=”fitFrame(this.id)” frameborder=”0” width=”100%”></iframe>
本屋で↑を立ち読みしたら(買え! >> 俺) 載ってた。
同じ結論になってたようなので、買わなくてもいいってことか?
~~追記終わり
ツイート