in reply to Best way to do Mixin Class

Do what you would in C++: multiple inheritance (into a subclass). A mixin class is really just a class providing behaviour. It lets you add particular methods to an existing class, without messing about with that class.

An example should make things clear...

Say we have (unrelated) classes Foo and Bar, each with a method val with similar semantics:
package Foo; sub new { my ($class) = @_; return bless [], $class; } sub val { my $self = shift; $self->[0] = $_[0] if @_; "Foo($self->[0])"; } package Bar; sub new { my ($class) = @_; return bless { val => 'nothing' }, $class; } sub val { my $self = shift; $self->{val} = $_[0] if @_; "Bar($self->{val})"; }
We'd like to have a method that prints the val, but we don't want to touch our 2 classes (maybe they're not our responsibility, or maybe we also need them unadorned, or whatever... that's why we want a mixin!). Here's the mixin:
# Something to mixin package Printer; sub print { my $self = shift; my $val = $self->val; print "Value is $val\n"; }
If we manage to get a Foo or a Bar to execute Printer::print, we get our desired behaviour.

Multiple inheritance to the rescue! Define Foos that are also Printers...

package Foo2; use vars '@ISA'; @ISA = qw(Foo Printer); package Bar2; use vars '@ISA'; @ISA = qw(Bar Printer);
Use them as you'd expect:
package main; my $x = new Foo2; my $y = new Bar2; $x->val(17); $y->val('xyzzy'); $x->print; $y->print;

Hope this helps...

Replies are listed 'Best First'.
Re: Re: Best way to do Mixin Class
by jcupp (Acolyte) on Apr 06, 2002 at 21:19 UTC
    Is it a good idea/possible to modify @ISA at run-time? I guess as long as you don't "use base ..."

      It's the traditional way (sorry, at least my 5.004 roots are showing). What I do is well-documented, e.g. in perlboot or perltoot.

      As long as you don't change @ISA while doing important stuff, it should be OK. But note the warning about changing @ISA in perlobj!

      In any case, using base can't be bad for you...