Halihallo Calocybe
Leider musste ich dies mal schmerzlich feststellen... Zudem finde ich es eigentlich falsch bzw. schlecht implementiert...
Das Vorkommen mehrerer Eigenschaften mit selbem Namen ist ein grundsaetzliches Problem bei Mehrfachvererbung, das auch schon zwischen zwei Basisklassen auf derselben Vererbungsebene auftreten kann. Ich glaube nicht, dass es dafuer eine allgemeingueltige Loesung gibt oder das man sagen koennte, welche der Suchstrategien als besser einzustufen ist.
Wie ist es denn bei anderen Sprachen implementiert?
Nun, ich kann dein Argument verstehen; es ist wohl auch etwas von der "Funktionsweise" des Programmes abhängig, was mehr Sinn macht. Nur für mein Projekt hatte ich folgendes:
Klasse Website extends DataNode (speicherung der Daten),
Website::Integrity (Datenintegrität wahren)
Website::Sync (Synchronisation mit anderem S.)
Eine Andere Klasse, welche vollständig von Website erbt, jedoch auch wieder durch Integrity und Sync erweitert werden
=> @ISA = qw(Website VWebsite::Integrity VWebsite::Sync);
Also, wenn ich jetzt die Methode checkIntegrity von VWebsite starte, wird er mir die entsprechende Integrity-Methode von Website->Website::Integrity aufrufen, was ja _falsch_ ist, da ich nicht die Integrität der Website sondern der virtuellen Website (VWebsite) testen will... Für meine Anwendung ist also das depth-first-Verfahren schlecht... Mir wäre es viel, viel lieber gewesen, wenn er zuerst in den basisklassen der "gleichen" Ebene gesucht hätte und erst dann in die Tiefe gegangen wäre...
Aber das Problem habe ich inzwischen gelöst (wenn auch unschön, wie ich gestehen muss). Ich habe die Modul-struktur sehr "logisch" gehalten, deshalb konnte ich dann folgendes machen:
sub getIntegrityClass {
my ($class) = @_;
if ((ref($class) eq 'SCALAR') or (ref($class) eq '')) {
# seems to be a class
# do nothing! - $class is already the classname
} else {
# seems to be an instance
$class = ref($class); # now $class is the classname
}
# $class is now something like: Anaxus::CampaignGroup::Default
# but getIntegrityClass should return Anaxus::Integrity::CampaignGroup::Default
# so, let us insert the 'Integrity::'...
my @class_dirs = split( /::/, $class );
shift @class_dirs; # don't care of the beginning 'Anaxus::'
unshift @class_dirs, 'Integrity'; # Insert the 'Integrity::'
unshift @class_dirs, 'Anaxus'; # let's reinsert the top-level 'Anaxus::'
$class = join( '::', @class_dirs); # rebuild the class-name
return $class; # and return it.
}
aufgrund des Klassennamens des Objektes bastle ich einfach die entsprechende Namen der entsprechenden Integrity und Sync Module...
Diese vorher gezeigte Methode befindet sich jeweils in den Basisklassen für Integrität und Synchronisation, da für die Integrität und Sync auch wieder verschiedene Klassen durcheinandererben... Mei, das war'n verzwicktes Zeug... Vererbungen über 7 Ebenen... Hat mir manchmal fast den Hals gebrochen ;)
Ich hätte natürlich auch einfach in jedes Modul eine Methode einbauen können, welche den gleichen String zurückgiebt, aber das war mir zuviel arbeit (sind ca. 30 Klassen); da mache ich lieber eine Methode an _einem_ Ort, die vielleicht etwas komplizierter ist...
Viele Grüsse
Philipp