moderated >> Adding methods to UNIVERSAL class

by Mark Hughes » Wed, 09 Mar 2005 02:05:24 GMT

Hi

I've been using Perl for a while but have just recently decided to try and
use the object oriented facilities that the language provides.

Been doing OK until I tried to add my own methods to UNIVERSAL. As I
understand it, when you call a method in a class Perl will go looking
through the superclasses listed in @ISA that might hold the method. When
that's exhausted then it will look in UNIVERSAL which is where all classes
are rooted.

To add your own methods to UNIVERSAL do you actually create a UNIVERSAL.pm
file/module/class containing the methods you need and if so where do you
store it??

Thanks
Sparky




moderated >> Adding methods to UNIVERSAL class

by Mark Jason Dominus » Wed, 09 Mar 2005 03:05:45 GMT


"Mark Hughes" < XXXX@XXXXX.COM >:

You could, but it would be much simpler just to put

sub UNIVERSAL::mymethod {
...
}

into any one of your source files.

moderated >> Adding methods to UNIVERSAL class

by John Bokma » Wed, 09 Mar 2005 04:43:50 GMT


Don't. Make your own class, and make it the base of your classes.


--
John MexIT: http://johnbokma.com/mexit/
personal page: http://johnbokma.com/
Experienced programmer available: http://castleamber.com/
Happy Customers: http://castleamber.com/testimonials.html

moderated >> Adding methods to UNIVERSAL class

by Heini » Wed, 09 Mar 2005 05:19:13 GMT


Here's one example of the many ways to do it - multiple packages in the
same file (Foo.pm here):

package UNIVERSAL;
sub non { isa($_[1], $_[0]) ? () : $_[0] }

package Foo;
sub bud {
unshift @_, __PACKAGE__->non($_[0]);
ref $_[0] ? shift->clone(@_) : shift->new(@_);
}
sub new ...

The function "non" defined here will be inherited by the subclasses of
Foo, even if they are in different .pm files (at least in Perl 5.6.1 it
does). That may be one of the reasons why John tells you not to.

I wish the "non" function would be included in UNIVERSAL out-of-the-box
t6hough. Maybe in the following form:

sub non { isa($_[1], $_[0]) ? ( wantarray ? () : undef ) : $_[0] }

Heini

moderated >> Adding methods to UNIVERSAL class

by Yitzchak Scott-Thoennes » Wed, 09 Mar 2005 07:22:06 GMT


First of all, note that adding methods to UNIVERSAL is not a "clean"
solution to any problem, because your method UNIVERSAL::Foo will
necessarily prevent anyone else from creating a UNIVERSAL::Foo for
some other purpose.

A UNIVERSAL.pm is already distributed with perl; it contains
documentation for the UNIVERSAL methods that perl provides (isa, can,
and VERSION), and allows them to be exported. You should not create a
conflicting UNIVERSAL.pm or alter perl's.

Remember that there's no forced connection between package names and
file names. You can just put UNIVERSAL methods in your own module's file:

MyMod.pm:
package MyMod;
...

{
package UNIVERSAL;
sub Foo {
...
}
}

1;

moderated >> Adding methods to UNIVERSAL class

by Mark Hughes » Wed, 09 Mar 2005 17:59:39 GMT

Hi all

Those tips are very useful for me and I can see now where I was going wrong.

Thanks for your time.

Regards
Sparky

Similar Threads

1. UNIVERSAL class like functionality for non-OO?

Hello list,
Is there a clean and elegant way to make a subroutine available to all 
namespaces/packages? Something like the UNIVERSAL class for objects, but 
for non-OO environment. I need to embed a logging facility into a 
multimodule project, so I want to have a certain function (say log_msg() 
) to be available anywhre in the program, without importing it in each 
and every module. 

Thanks
Peter

2. Class::DBI and UNIVERSAL::moniker

3. Tricky subclassing problem: Parent class method uses static value from child class

I want to be able to do something along the lines of:

package A;
@ISA = ('B');
use Class::Std;

my $foo='this';

package C;
@ISA = ('B');
use Class::Std;

my $foo='this';

package B;
use Class::Std;

sub method {
  do something with $foo
}

(obviously, there's a bit more to this, but I'm trying to abstract
things as much as possible).

But I can't seem to find anyway to make $bar->method(); see the
appropriate value of $foo depending on whether $bar is an object of
type A or C. Am I going to have to have a method (or AUTOMETHOD) to
copy $foo into the B namespace when method is called? Or is there a
more elegant way of handling this? [As a note, in actuality, I'm
dealing with a %foo rather than a $foo].

4. Overriding a class method with an object method