Here's a slightly more complex version that creates
actual methods on the fly so that you avoid the overhead
of an AUTOLOAD method call on the second and successive
calls.
It also uses magic GOTO, which is a cool hack in itself.
#!/usr/bin/perl -w
package myClass;
use strict;
use vars qw{$AUTOLOAD $Debug};
$Debug = 1;
sub new {
return bless {
thing => 1,
thang => 2,
thong => 3,
}, shift;
}
sub AUTOLOAD {
my $self = shift or return undef;
# Get the called method name and trim off the fully-qualified part
( my $method = $AUTOLOAD ) =~ s{.*::}{};
# If the data member being accessed exists, build an accessor for it
if ( exists $self->{$method} ) {
### Create a closure that will become the new accessor method
my $accessor = sub {
my $closureSelf = shift;
if ( @_ ) {
return $closureSelf->{$method} = shift;
}
return $closureSelf->{$method};
};
# Assign the closure to the symbol table at the place where the real
# method should be. We need to turn off strict refs, as we'll be mucking
# with the symbol table.
SYMBOL_TABLE_HACQUERY: {
no strict qw{refs};
*$AUTOLOAD = $accessor;
}
# Turn the call back into a method call by sticking the self-reference
# back onto the arglist
unshift @_, $self;
# Jump to the newly-created method with magic goto
goto &$AUTOLOAD;
}
### Handle other autoloaded methods or errors
}
DESTROY {}
### Test program
package main;
my $a = new myClass;
print $a->thing, $a->thang, $a->thong, "\n";