> > некий код:
> >
> > sub method
> > {
> >    my $self = shift;
> >    ...
> >    $self->{handle} = AnyEvent::Handle fh => $fh, on_error => sub {
> > $self->{error} = $! };
> >    ...
> > }
> >
> > получается что каллбек цепляет ссылку на $self и из за него деструктор
> > вызван не может быть до тех пор пока handle не уничтожится.
> > в случае с просто ссылками - понятно: weaken на них. а здесь куда можно
> > weaken натравить чтобы деструктор у такого объекта работал?
>
> После $self = shift; добавить weaken($self);
>

В этом случае если эта работа делается внутри конструктора, то добавление
такого weaken приводит к тому что вместо указателя на объект возвращается
какая-то ахинея.

вот такой тест:

#!/usr/bin/perl

use warnings;
use strict;

use utf8;
use open qw(:std :utf8);

package TestW;
use AnyEvent::Handle;
use Scalar::Util qw(weaken);


sub new {
    my ($class, $fh) = @_;

    my $self = bless {  } => $class;
#     weaken $self;
    $self->{handle} = new AnyEvent::Handle
        fh => $fh,
        on_error => sub { $self->{error} = $! };
    return $self;
}

package main;
use Data::Dumper;

my $o = new TestW(\*STDIN);
print Dumper $o;

печатает на выходе следующее:

$VAR1 = bless( {
                 'handle' => bless( {
                                    '_activity' => '1298875336.78856',
                                    '_ractivity' => '1298875336.78856',
                                    '_wactivity' => '1298875336.78856',
                                    'fh' => \*::STDIN,
                                    'oobinline' => 1,
                                    'on_error' => sub { "DUMMY" }
                                  }, 'AnyEvent::Handle' )
               }, 'TestW' );

теперь если раскоментировать weaken, то объект превратится в простой хеш:

$VAR1 = {
          'handle' => bless( {
                             '_activity' => '1298875430.28919',
                             '_ractivity' => '1298875430.28919',
                             '_wactivity' => '1298875430.28919',
                             'fh' => \*::STDIN,
                             'oobinline' => 1,
                             'on_error' => sub { "DUMMY" }
                           }, 'AnyEvent::Handle' )
        };

и как быть?
Perl 5.10.1
--
Moscow.pm mailing list
[email protected] | http://moscow.pm.org

Ответить