Object-Oriented Perl

Anton Berezin


Object-oriented programming


A language mechanism for binding data with methods that operate on that data. Method invocation is often referred to as "sending a message to the object".

Classic OOP Perl


To get objects in Perl, we need to store the data somewhere, and associate that data with methods.



Perl already has references to arbitrary data structures.

my $hashref = {
	a  =>  1,
	b  =>  2,

Code references

Perl already has references to arbitrary data structures.

Including references to functions.

sub x { return 42; }

my $funcref = \&x;
print $funcref->();

Objects by hand

So we can do a poor man OO like this:

sub method1 {
	my ($obj) = @_;
	print "Attr1 is $obj->{attr1}\n";
sub method2 { ... }

my $obj = {
	attr1 => 1,
	attr2 => 2,
	method1 => \&method1,
	method2 => \&method2,


Objects by hand

This is UGLY.

(although it has an advantage of not needing an OO language)

One can write such objects in C, if one wants.

(yes, people are known to do just that)

(I've done that myself)

Syntactic help from the language


We need a special syntax for method calls.

But not much


But beyond the method calls syntax, we need surprizingly little.

Object representation

The "real" objects in Perl are still references.

A reference to pretty much anything can be made into an object.

How to associate an object with a class

Perl has namespaces (packages)

That's what normally used to create modules

But it can work for classes, too.

Blessing a reference

Special builtin called bless

bless $reference, Classname;
$reference is any reference. Classname is any package name.

The result is a blessed reference; an object.

Methods of an object

Methods are just ordinary subs defined in the class'es package.

Call them using dereferencing arrow:

$obj->method($param1, $param2);
The very first parameter passed will be an object reference.

Put it together

package MyClass;

sub my_method
	my ($self, $param) = @_;
	if ($self->{attr1} > $param) {
		print "I am the greatest\n";
	} else {
		print "I am the leanest\n";

my $o = bless { attr1 => 42 }, 'MyClass';
$o->my_method(17);     # I am the greatest
$o->my_method(137);    # I am the leanest

That's it



That's it

Thank you.


Thank you!


Any questions?

Thank you.


Thank you!


Any questions?


Just kidding.

Accessing the data

Since an object is still a reference, the underlying data are easily accessible.

$o->{attr1} = 42;

No protection

Any code outside of the class can easily tinker with internal object representation.

This is considered bad.

Class methods

The same syntax $o->methodname can be used to call class methods.

The only difference is that the package name is used instead of the object reference


Method calls sidenote

Actually, anything that resolves to either a blessed reference or to a package name can be used with the method call syntax:

my $pkg = "Some::Package";
$pkg->method(...);   # OK

funcall()->{hashkey}->method(...);  # OK


Constructors are simply class methods that return an object.

Constructors' names can be arbitrary, although new() and create() are prevalent.

package MyClass;

sub new {
	bless { attr1 => 42 }, 'MyClass';

Better constructors

Since constructor is typically called with a method call syntax, its first parameter will be class name.

package MyClass;

sub new {
	my ($class) = @_;
	bless { attr1 => 42 }, $class;



What about inheritance?

Luckily, the method call syntax in combination with a little extra feature takes care of that.


Enter @ISA array.

It is a package global.

package MyInheritedClass;
use vars qw(@ISA);
@ISA = qw(MyClass);

sub my_method2 { ... }

@ISA cont.

When an object or class method is called, Perl gets the package name and tries to find a sub in that package with the same name as the method.

If found, it calls that.

If not, it looks up the @ISA array for other packages, and tries to find the method in it.


All classes implicitly inherit from class "UNIVERSAL" as their last base class.

Which has some handy methods, mainly for introspection.

Shortcut for inheriting

It is a little bit tedious to write

use vars qw(@ISA);
@ISA = qw(MyClass);

so there is a shortcut:

use base 'MyClass';

Calling inherited methods

We can of course do

package MyInheritedClass;
sub method1
	my ($self) = @_;
	# do something
	# do something else

But this is not OOish.

Besides, it won't work if MyClass does not have sub method1 {}, inheriting it from some other class.

SUPER pseudo-class

The right thing to do would be

package MyInheritedClass;
sub method1
	my ($self) = @_;
	# do something
	# do something else

SUPER can only be used with this syntax.

SUPER refers to the current package ancestor.

So don't use it outside of object methods.

Inheriting constructors

A properly written base class constructor will bless the reference into the right class, so we just need to do some initializing:

package MyInheritedClass;
sub new {
	my ($class, %params) = @_;
	my $self = $class->SUPER::new(%params);
	# do something else with params...
	return $self;

In many cases such constructors are not needed.


Perl has automatic garbage collection, so in many cases destructors are not needed.

When they are, create a sub called DESTROY


	my ($self) = @_;
	# free some resources


my $h = { a => 1 };
my $a = [1,2,3];
my $s = \3;
my $f = \&somesub;
my $g = \*STDOUT;
my $o = bless {}, "MyClass";


print "$h\n";   # HASH(0x840016c)
print "$a\n";   # ARRAY(0x8400afc)
print "$s\n";   # SCALAR(0x8400be0)
print "$f\n";   # CODE(0x8400d30)
print "$g\n";   # GLOB(0x8400820)
print "$o\n";   # MyClass=HASH(0x8400d24)


print ref $h, "\n";   # HASH
print ref $a, "\n";   # ARRAY
print ref $s, "\n";   # SCALAR
print ref $f, "\n";   # CODE
print ref $g, "\n";   # GLOB
print ref $o, "\n";   # MyClass


sub is_a {
	my ($o, $isaclass) = @_;
	my $class = ref $o || $o;
	return 1 if $class eq $isaclass;
	for my $inhc (eval "\@$class\::ISA") {
		return 1 if is_a($inhc, $isaclass);
	return 0;


Luckily, the UNIVERSAL package already provides isa for us.

	if ($some_object->isa("AnyClass")) {

	if (SomeClass->isa("AnyClass")) {


Sometimes we need to know whether a particular object has a certain method.

	if ($some_object->can("drink")) {

	if (SomeClass->can("dance")) {

Indirect method call syntax

	print STDERR "A horrible error\n";

	print STDERR, "Yes indeed\n";

The same syntax got hijacked for objects

Indirect method call syntax

	my $o = MyClass->new(...);

	my $o = new MyClass ...;

Means the same thing.


Multiple inheritance

What about multiple inheritance?


Just put more stuff into the @ISA.

@ISA = qw(Class1 Class2);


use base qw(Class1 Class2);

Multiple inheritance

Conflicts resolution?

Deep-first tree search.

But can be overriddent by CPAN modules (Class::C3).

Conclusions for "classical" OO Perl

Classical OO in Perl: a bit ugly.

Looks like bolted on.

IS bolted on.

Easy to understand.

Almost no magic - just reference blessing.

Surprizingly flexible.

Data storage for objects

Most objects use hashrefs.

Convenient - any amount of data can be associated with an object.

But no protection.

Data storage for objects

But can be any ref.

Data storage as arrays

Array references are used sometimes.

One reason - efficiency, since array access is much faster than hash access.

Another reason - memory use, arrays typically are much smaller.

Not very convenient:

my $o = bless [1,2,3], MyClass;

$o->[0] = 42;   # what's that?
$o->[1] = 137;  # and this?

Data storage as arrays

One can use Class::ArrayObjects (and no doubt ten other CPAN modules) to somewhat alleviate the problem.

package MyClass;

use Class::ArrayObjects define => {
	fields => [qw(hest foo bar)],

my $o = ...;

$o->[hest] = 42;

Data storage as arrays


Still not protected. But harder to tinker with.

Data storage as scalar ref

Data storage as scalar ref - why?

Typically for really simple stuff.

Like counter class.

But also has other uses; more on that later.

Counter class

Counter class

package Counter;

sub new {
	my ($class, $initial) = @_;
	bless \$initial, $class;
sub get { my $self = shift;  $$self }
sub inc { my $self = shift;  $$self++ }
sub dec { my $self = shift;  $$self-- }

Data storage as filehandle

Data storage as filehandle.

Used in special cases.

Example: Net::Telnet module.

Data storage as sub ref

Data storage as sub ref.

This one can be used to protect data.

But the method is quite ugly.

The idea is to call the sub to get to the data.


package SubCounter;
sub new
	my ($class, $init) = @_;
	bless sub {
		die "We exist to protect.\n"
			unless (caller)[0] eq "SubCounter";
		return \$init;
	}, $class;
sub get { ${$_[0]->()} }
sub inc { ${$_[0]->()}++ }
sub dec { ${$_[0]->()}-- }

ProtectedCounter example

my $c = new SubCounter 42;
print $c->get, "\n";
print $c->get, "\n";
my $ref = $c->();  # dies here
print $c->get, "\n";

A note of caution

A note of caution.

Do not over-do OO Perl.

Use objects where it makes sense.


    String::Koremutake -
    Convert to/from Koremutake Memorable Random Strings
    use String::Koremutake;
    my $k = String::Koremutake->new;

    my $s = $k->integer_to_koremutake(65535);
    # botretre
    my $i = $k->koremutake_to_integer('koremutake');
    # 10610353957

What's the point of that??


Good OO modules provide accessors where needed.

package MyClass;
sub new { ... }
sub hest { $_[0]->{hest} }
sub set_hest { $_[0]->{hest} = $_[1] }
sub foo { $_[0]->{foo} }
sub set_foo { $_[0]->{foo} = $_[1] }

Gets boring, FAST.

Accessors, improved

package MyClass;
sub new { ... }
sub hest { defined $_[1] ? $_[0]->{hest} = $_[1] : $_[0]->{hest} }
sub foo { defined $_[1] ? $_[0]->{foo} = $_[1] : $_[0]->{foo} }

Still boring.

Accessors, improved++

sub _gen_accessor {
	my $aname = shift;
	eval "sub $aname { defined \$_[1] ?
		\$_[0]->{$aname} = \$_[1] :
		\$_[0]->{$aname} }";
_gen_accessor($_) for qw(hest foo bar baz);

Now we have something.

Accessors, via CPAN

Accessors, via CPAN.

There's of course a brazillion of CPAN modules that will do that for you.

Sometimes I hate TIMTOWTDI.



package MyClass;
use base qw(Class::Accessors);
MyClass->mk_accessors(qw(hest foo));

my $o = MyClass->new({ hest => 42,
	foo => 137});
print $o->hest;

It also provides new for you.

Singleton classes

Sometimes what you want is that no more than one instance of the object exists in a program.

Example: print spooler.

Singleton classes, by hand

package MySingleton;

my $obj;

sub new { $obj ||= bless {}, $_[0] }

Singleton classes, CPAN

Or use Class::Singleton

Just derive from it.

package MySingleton;
use base 'Class::Singleton';

sub method1 { ... }

Default objects

Sometimes you wish to provide both procedural and OO interface.

In this case it is quite natural for the procedural interface to use a "default" object and then just call OO interface.

Or at least do something to the same effect.

Default objects: CGI.pm

The classic example would be CGI.pm:

use CGI qw/:std/;

my $q = new CGI;
print $q->header, $q->start_html;

use CGI qw/:std/;

print header, start_html;

Default objects, by hand

package MyDefault;

my $def;

sub new { ... }

sub do_something
	my $self = shift if ref($_[0]) && $_[0]->isa("MyDefault");
	$self ||= $def ||= new MyDefault;

	# now do something

Default objects, by hand

So either

my $o = new MyDefault;




will work.

Default objects, CPAN

But of course there is (ARE) CPAN modules to do that.

For example, Class::Default.

More introspection

Class::ISA provides a function that goes through a complex hierarchy of classes and returns a list of all classes that will be searched by the method dispatcher in the order they will be searched.

plus variants of the above

More introspection

Class::Inspector provides a bunch of functions to extract useful information about a class:

More introspection

Class::Handle is a mix of UNIVERSAL, Class::ISA, and Class::Inspector.

Base classes

Class::Base provides a number of useful predefined subs:

Use it if you need those


Sometimes an object holds instances of other objects as its attributes. Sometimes one wishes to delegate calls to certain methods of the object to one of the other objects it holds.

Delegation by hand

Delegation by hand is easy to do:

sub meth1 {
    my $self = shift;

sub meth2 {
    my $self = shift;


Class::Delegation does it for us:

use Class::Delegation
   send => 'meth1',
   to   => 'obj1',
   as   => 'some_meth',

   send => -OTHER,
   to   => 'fallbackobj';
Very useful.


Have a look at Class::Spiffy and at Moose


Inside-out objects

Inside-out objects is another way to do the protection of the internal object state.

Instead of using a hashref per object, which is indexed by attribute names to access object attributes, inside-out objects use a private hash per attribute which is indexed by object reference.

Inside-out objects


$o1->{hest} = 42;
$o1->{foo} = "moof";
$o2->{hest} = 137;
$o2->{foo} = "foom";


my (%hest, %foo);
$hest{"$o1"} = 42;
$foo{"$o1"} = "moof";
$hest{"$o2"} = 137;
$foo{"$o2"} = "foom";

Inside-out objects

Since %hest and %foo are private, this approach provides a pretty good protection mechanism in comparison with the traditional Perl OO.

Even derived classes cannot tinker with our attributes.

It is also practically as efficient as the "normal way".

Since the reference is only used as the unique key, we can use a scalar reference (it's cheap)

Inside-out objects

package MyInsideOut;

my %hest;
my %foo;

sub new { bless \(my $dummy), $_[0] }
sub set_hest { $hest{"$_[0]"} = $_[1] }
sub hest { $hest{"$_[0]"} }

Inside-out objects

We need DESTROY to cleanup.

	delete $hest{"$_[0]"};
	delete $foo{"$_[0]"};

Inside-out objects

Another advantage of inside-out objects is that we get compile-time checking of typos:

use strict;
$normal_obj->{tpyo_count}++;   # OK

use strict;
$tpyo_count{$inside_out_obj}++;   # %tpyo_count is unknown

Inside-out objects, CPAN

Use one of:


Another way to use a closure to get decent data protection.

It does not represent the class as the closure.

But the methods are closures.

All in all, pretty nifty.


package FurryAnimal;
use Class::Closure;

sub CLASS {
	extends HairlessAnimal;

	has my $hair;

	method shave => sub {
		$hair = undef;

Objects with dynamic methods

Using Class::Prototyped, one can dynamically add methods and attributes to an existing, instantiated object.

One can also have objects inherit their behavior and state from another object.

So one can clone, then modify the behavior.

Thank you.


Thank you!


Any questions?