Packages and __PACKAGE__

[ Perl tips index ]
[ Subscribe to Perl tips ]

The default name space in Perl is called main. Unless Perl is directed otherwise, all subroutines and variables are added to the main name space.

To create a new name space in Perl (also called a package) we use the package keyword. Using different name spaces allows us to separate our code into logical parts where we can have identically named subroutines and variables if required. For example we may have a Client package which includes subroutines for name, address, and phone_number as well as a PTA package (for Perl Training Australia) with the same subroutines.

        package Client;

        sub name {
                my ($self) = @_;

                return "Awesome Cliens R Us";
        }

        sub address {
                my ($self) = @_;

                my $address = $self->house_no() . " " .
                              $self->street_name . "\n". 
                              $self->suburb() . " " . 
                              $self->state() . "\n".
                              $self->postcode;

                return $address;
        }

        sub phone_number {
                my ($self) = @_;

                return "+61 3 1234 1234";
        }

        # and elsewhere
        package PTA;

        sub name {
                return "Perl Training Australia";
        }

        sub address {
                return "104 Elizabeth Street\nCoburg Victoria\n3058";
        }

        sub phone_number {
                return "+61 3 9354 6001";
        }

To access the different subroutines in our later code we prefix the subroutine name with the name of the package.

        # Print PTA's address
        print PTA::address();

When writing Perl objects, a class is just a package. Thus in object oriented coding we can omit the name of the package if our object is from that class.

        my $client = Client->new();  # Assumes existance of 'new'
        
        # Print client's address
        print $client->address();

__PACKAGE__

Sometimes you may find yourself writing the package name out multiple times inside your package. For example, when using Class::DBI we might write:

        package Music::Artist;

        # Inherit from the Music::DBI class (defined elsewhere)
        use base 'Music::DBI';

        # These records are pulled from this database table
        Music::Artist->table('artist');

        # We care about these columns
        Music::Artist->columns(All => qw/artistid name/);

        # Each artist may have many CDs
        Music::Artist->has_many(cds => 'Music::CD');

As with any code repetition this can lead to errors should we later decide to change our package name, or if someone should cut and paste our code. To avoid these errors Perl gives us the __PACKAGE__ constant which contains the name of the current package.

This allows us to rewrite the above as follows:

        package Music::Artist;

        # Inherit from the Music::DBI class (defined elsewhere)
        use base 'Music::DBI';

        # These records are pulled from this database table
        __PACKAGE__->table('artist');

        # We care about these columns
        __PACKAGE__->columns(All => qw/artistid name/);

        # Each artist may have many CDs
        __PACKAGE__->has_many(cds => 'Music::CD');

__PACKAGE__ and hashes

If you attempt to use the value from __PACKAGE__ as a hash key you may find that things don't turn out exactly as you expect. Writing:

        # Doesn't work as intended
        $hash{__PACKAGE__} = 1;

will create the key __PACKAGE__ inside your hash rather than the name of your package. This is because whenever a hash gets a bareword as its key it immediately treats that as a string. Thus the following two statements are the same.

        # These are equivalent
        $hash{__PACKAGE__} = 1;
        $hash{"__PACKAGE__"} = 1;

To use the value from __PACKAGE__ as a hash key, you need to tell Perl to evaluate the constant first. We can do this by adding an empty string to the constant, or by saving it into a variable first:

        # Using our package name as a key inside our hash
        $hash{__PACKAGE__ . ""} = 1;

        my $package = __PACKAGE__;
        $hash{$package} = 1;

Accidently creating a __PACKAGE__ key rather than one from the name of your package is a very common mistaken which can lead to very subtle and hard-to-track down bugs. If you are uncertain, remember to use Data::Dumper on your hash to ensure that you're getting the keys you want.

[ Perl tips index ]
[ Subscribe to Perl tips ]


This Perl tip and associated text is copyright Perl Training Australia. You may freely distribute this text so long as it is distributed in full with this Copyright noticed attached.

If you have any questions please don't hesitate to contact us:

Email: contact@perltraining.com.au
Phone: 03 9354 6001 (Australia)
International: +61 3 9354 6001

Valid XHTML 1.0 Valid CSS