Skip to content

Instantly share code, notes, and snippets.

@jberger
Last active December 12, 2015 07:58
Show Gist options
  • Save jberger/4740303 to your computer and use it in GitHub Desktop.
Save jberger/4740303 to your computer and use it in GitHub Desktop.
lvalue accessors
#!/usr/bin/env perl
use strict;
use warnings;
use v5.10;
package Moo::LvalueAccessor;
use Scalar::Util qw/weaken/;
use parent 'Exporter';
our @EXPORT = 'AUTOLOAD';
sub TIESCALAR {
my ($class, $attr, $invocant) = @_;
weaken( my $self = $invocant );
my $curry = sub {
return unless $self;
$self->$attr(@_);
};
bless $curry, $class;
}
sub FETCH { $_[0]->() }
sub STORE { $_[0]->($_[1]) }
sub AUTOLOAD :lvalue {
my $self = shift;
my $attr = '_' . (split /::/, our $AUTOLOAD)[-1];
return unless $self->can($attr);
tie my $var, __PACKAGE__, $attr => $self;
$var;
}
package Person;
use Moo;
Moo::LvalueAccessor->import; # use Moo::LvalueAccessor
has '_money' => (
is => 'rw',
default => sub { 0 },
init_arg => 'money',
);
sub payday {
my ($self, $amount) = @_;
$self->money += $amount;
}
package main;
my $person = Person->new;
$person->payday( 200 );
$person->payday( 400 );
say $person->money;
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment