2016-04-29 6 views
0

Im Rahmen des Code-Refactoring, habe ich einige Code Duplikate gefunden, die ichSchnittstelle Vererbungshierarchie

Ich habe eine Schnittstelle wie eine unten, in einer Baugruppe zu entfernen, versuche ich kann nicht ändern.

public interface IArtifact 
{ 
    void Accept(IArtifactVisitor visitor); 
} 

public interface IArtifactVisitor 
{ 
    void Visit(Topic topic); 
} 

In den Referenzen Versammlung, die ich dort vorhandene Schnittstellen wiederverwendet werden soll ist die gleiche Funktion Unterschrift

public interface IArtifact 
{ 
    void Accept(IArtifactVisitor visitor); 
} 

public interface IArtifactVisitor 
{ 
    void Visit(Topic topic); 
    void Visit(NewTopic topic); 
} 

und Akzeptieren der sieht so etwas wie dieses

public void Accept(IArtifactVisitor visitor) 
{ 
    visitor.Visit(this); 
} 

Um entfernt die Codewiederverwendung, habe ich das folgende versucht:

public interface MyIArtifact : IArtifact 
{ 
    void Accept(MyIArtifactVisitor visitor); 
} 

public interface MyIArtifactVisitor : IArtifactVisitor 
{ 
    void Visit(NewTopic topic); 
} 

aber, was das tut, ist, es zwingt mich, in jeder Implementierungsklasse zu implementieren beide Accept (MyIArtifactVisitor Besucher) und Accept (IArtifactVisitor Besucher)

ein besserer Weg, dies Gibt es zu tun?

+2

Sie können eine gemeinsame Basisklasse (abstrakt oder nicht) erstellen, die diese Schnittstellen implementiert und von ihr erbt. – Igor

+0

Ich fürchte, ich verstehe nicht, was Sie versuchen zu tun. Welche Codeduplizierung haben Sie derzeit anders als die "doppelten" Interfaces in referenzierten Assemblies (worüber Sie nicht wirklich viel machen können) –

+0

Dies ist ein Beispiel für ein Pattern, das wiederholt wird, zum Beispiel void Visit (Topic topic) ist dupliziert, über Schnittstellen –

Antwort

1

Das Besuchermuster ist verkorkst, und meiner Meinung nach ist es nicht sinnvoll, es über Schnittstellen zu implementieren. Die Art und Weise Besuchermuster zu implementieren ist wie folgt:

abstract class Artifact{ 
    internal abstract void Visit(ArtifactVisitor visitor); 
} 


class Topic : Artifact{ 
    internal override void Visit(ArtifactVisitor visitor) 
    { 
     visitor.Visit(this); 
    } 
} 

class ArtifactVisitor{ 
    internal virtual void Visit(Artifact artifact) 
    { 
     artifact.Visit(this); 
    } 
    protected virtual void Visit(Topic topic) 
    { 
    } 
} 

class SomeSpecificTopicVisitor : ArtifactVisitor 
{ 
    protected override void Visit(Topic topic) 
    { 
     //do something with topics 
    }  
} 

Von diesem Zustand können Sie Ihre eigenen Besucher aus ArtifactVisitor starten vererben. Sie überschreiben nur die Methoden, die Sie tatsächlich benötigen.

Das Besuchermuster ist nicht sehr erweiterbar. Es ist nur nützlich, wenn die Gruppe von Erben fest ist und sich nicht wesentlich ändert. Nichtsdestotrotz, wenn Sie es richtig verwenden, wird es Ihre doppelten Dispatching-Probleme gut lösen.

4

Wenn ich Ihre Frage richtig verstanden, Sie benötigen nur eine Methodensignatur in Ihrer Schnittstelle es

public interface MyIArtifactVisitor : IArtifactVisitor 
{ 
    void Visit(NewTopic topic); 
} 

Und das ist im Wesentlichen zu spezifizieren. Also, wenn Sie das impliment möchten, und die externe Schnittstelle, dann tun Sie so etwas wie die folgenden

public class MyImplimentingClass : MyIArtifactVisitor, IArtifactVisitor 
{ 
    public void Visit(NewTopic topic) 
    {} 

    public void Visit(Topic topic) 
    {} 
} 
Verwandte Themen