#!/usr/bin/perl use strict; use warnings; package BaseballPlayer; use Carp; my %attrib; sub BEGIN { %attrib = map { $_ => 1 } qw( RBI Batting_Average Hits Runs Stolen_Bases Games_Played ); no strict 'refs'; for my $n ( keys %attrib ) { *$n = sub { $_[0]->{$n} } } } sub new { my( $class, %arg ) = @_; exists $attrib{$_} or croak "Unknown stat: $_" for keys %arg; $arg{$_} ||= 0 for keys %attrib; bless \%arg, $class; } package BaseballPlayer::Pitcher; our @ISA = 'BaseballPlayer'; { my %object; sub new { my( $class, %arg ) = @_; my %pitcher_stat = map { $_ => delete $arg{$_} || 0 } qw( ERA Strikeouts ); my $base = BaseballPlayer->new(%arg); my $ret = bless $base, $class; $object{$ret} = \%pitcher_stat; $ret; } sub ERA { $object{$_[0]}{ERA} } sub Strikeouts { $object{$_[0]}{Strikeouts} } sub DESTROY { delete $object{$_[0]} } } package main; my $p = BaseballPlayer::Pitcher->new( Hits => 23, ERA => 4.32 ); print $p->Hits, "\n"; print $p->ERA, "\n";