By way of an answer to your actual questions I knocked this up.
#! perl -slw use strict; package Cish::Person; use Class::InstanceVariables qw( $first $last $middle ); sub new{ my $class = shift; local $self = instance(); ( $first, $middle, $last ) = @_; $self; } sub full_name{ local $self = shift; "$last, $first $middle"; } sub marry{ local $self = shift; my $spouse = shift; "$first married " . $spouse->first(); } package Perlish::Person; sub new{ my $class = shift; my $self = {}; @{ $self }{ qw[ first middle last ] } = @_; bless $self, $class; } sub full_name{ my $self = shift; join ' ', @{ $self }{ qw[last first middle ] }; } sub marry{ my $self = shift; my $spouse = shift; "$self->{ first } married " . $spouse->{ first }; } package main; use Benchmark qw[ cmpthese ]; my %tests = ( Cish => q[ my $john = new Cish::Person(qw(John F Jones)); my $sue = new Cish::Person(qw(Suzy P Edwards)); print STDERR $john->full_name(); print STDERR $sue->full_name(); print STDERR $john->marry($sue); ], Perlish => q[ my $john = new Perlish::Person(qw(John F Jones)); my $sue = new Perlish::Person(qw(Suzy P Edwards)); print STDERR $john->full_name(); print STDERR $sue->full_name(); print STDERR $john->marry($sue); ], ); cmpthese( -3, \%tests );
Results:
P:\test>300051 2>nul Rate Cish Perlish Cish 441/s -- -63% Perlish 1206/s 174% --
I made a few minor mods to your module in order to track down some warnings that were being issued.
use strict; package Class::InstanceVariables; sub import{ my $class = shift; my $caller = caller(); my $ties = <<"EOH" # line 1 "@{[__PACKAGE__]} eval @ line @{[__LINE__]}" package $caller; no strict; EOH . <<'EOS'; $self=''; sub TIESCALAR{ my $class = shift; my $var = shift; bless \$var, $class; } sub FETCH{ my $thing = shift; $self->{ $$thing }; } sub STORE{ my $thing = shift; $self->{ $$thing } = shift; } EOS no strict 'refs'; *{$caller."::self"} = \${$caller."::self"}; foreach my $ivar (@_) { if($ivar!~/^\$([A-Za-z_]\w*)$/) { die "$ivar is not a valid variable name!\n"; } my $varname = $1; *{$caller."\:\:$varname"} = \${$caller."\:\:$varname"}; $ties .= "sub $varname : lvalue { \$_[0]->{$varname} }\n"; $ties .= "tie \$$varname,'$caller','$varname';\n"; } *{$caller."::instance"}=sub{ bless {}, $caller; }; eval $ties; if ($@) { die $@; } } 1;
In terms of the danger of using local, I'm not sure there are any beyond forgeting and typing my $self; instead of local $self; which might not be a problem if you are the only user, but lack of familiarity might give me a problem, at least at first. The danger here is that not localising it causes fairly obscure bugs without any nice warnings to give you a hint what to look for.
As for whether I would actually use your module, I don't think so. Comparing the two (admittedly simplistic) versions of the modules, I'm not particularly convinced that the benefits outweight the penalties. The volume of typing and indirection involved seems pretty similar to me.
Whether his would remain true once you'd added some error checking, accesssor methods and the like I can't really visualise, but the reduction in typing would have to be pretty substantial to offset the close to 3x slowdown I think.
I'm not particularly enamoured with the status quo of perl OO syntax and semantics either. I would prefer verifiable lvalue-able, interpolatable, class members -- be they variables or functions -- but I haven't seen or come up with anything that satisfies all my desires in this regard yet. I think it may have to wait for Perl 6.
In reply to Re: Overhead vs. ease of use in OOP
by BrowserUk
in thread Overhead vs. ease of use in OOP
by fletcher_the_dog
| For: | Use: | ||
| & | & | ||
| < | < | ||
| > | > | ||
| [ | [ | ||
| ] | ] |