Beefy Boxes and Bandwidth Generously Provided by pair Networks
Perl: the Markov chain saw
 
PerlMonks  

Re^2: Self creating OO Module field accessors...

by hv (Parson)
on Jan 13, 2006 at 11:41 UTC ( #522955=note: print w/replies, xml ) Need Help??


in reply to Re: Self creating OO Module field accessors...
in thread Self creating OO Module field accessors...

What you also can do is:

for my $prop (qw [field1 field2 field3]) { eval sprintf <<'END', ($prop) x 3; sub %s { my $self = shift; if (@_) {$self->{%s} = shift}; return $self->{%s}; } } END }

I used to generate accessors in this way, in part because I felt that glob manipulation was scary and turning off strictness, however temporarily, was fragile. Tom Christiansen eventually managed to convince me that the eval approach is bad - firstly it is wasteful of memory (and processor) because each method is recompiled afresh; secondly because it is deferred, and so a perl -c check won't show problems.

So these days I do it more like this:

for my $method (qw/ field1 field2 field3 /) { no strict 'refs'; *$method = sub { use strict 'refs'; my $self = shift; if (@_) {$self->{$method} = shift}; return $self->{$method}; }; }

Rather than creating 3 independent blocks of code, this creates 3 closures over the same block of code; in practice the resulting methods are otherwise identical. I also feel they are much easier to read this way, which is another aid for debugging and maintenance.

(I saw an alternative approach to the strictness here recently:

for my $method (qw/ ... /) { my $sub = sub { the code ... }; no strict 'refs'; *$method = $sub; }
.. which is probably better, but I haven't started using it yet.)

See Re: Things I Don't Use in Perl for some other things my autogenerated methods do.

Hugo

Replies are listed 'Best First'.
Re^3: Self creating OO Module field accessors...
by demerphq (Chancellor) on Jan 13, 2006 at 13:07 UTC

    IMO There is a big advantage to the first style however: it actually defines the subs in such a way that you don't get weird error messages about stuff happening in an anon sub. Likewise you can set breakpoints in the debugger and stuff with the former but with the latter its not so easy. There are ways around this, but they aren't straight-forward.

    use Carp qw(confess); local *foo=sub { confess "What the fook!" }; eval qq[sub bar { confess "What the wook!" } 1 ] or die "failed to eval code: $@"; eval { foo(); 1 } or print $@; eval { bar(); 1 } or print $@; __END__ What the fook! at c:\temp\die.pl line 3 main::__ANON__() called at c:\temp\die.pl line 9 eval {...} called at c:\temp\die.pl line 8 What the wook! at (eval 1) line 1 main::bar() called at c:\temp\die.pl line 13 eval {...} called at c:\temp\die.pl line 12
    ---
    $world=~s/war/peace/g

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: note [id://522955]
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others exploiting the Monastery: (2)
As of 2022-05-28 01:25 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?
    Do you prefer to work remotely?



    Results (98 votes). Check out past polls.

    Notices?