6

J'essaie essentiellement de mettre en œuvre un modèle de stratégie, mais je veux passer différents paramètres à la mise en œuvre des « interfaces » (qui héritent du même objet) et ne sais pas si c'est possible. Peut-être que je choisis le modèle mal, je reçois une erreur semblable àModèle de stratégie avec des paramètres différents dans l'interface (C#)

'StrategyA' fait avec le code ci-dessous

membre abstrait implémente pas hérité 'DoSomething void (BaseObject)':

abstract class Strategy 
{ 
public abstract void DoSomething(BaseObject object); 
} 

class StrategyA : Strategy 
{ 
public override void DoSomething(ObjectA objectA) 
{ 
    // . . . 
} 
} 

class StrategyB : Strategy 
{ 
public override void DoSomething(ObjectB objectB) 
{ 
    // . . . 
} 
} 

abstract class BaseObject 
{ 
} 

class ObjectA : BaseObject 
{ 
// add to BaseObject 
} 

class ObjectB : BaseObject 
{ 
// add to BaseObject 
} 

class Context 
{ 
    private Strategy _strategy; 

// Constructor 
public Context(Strategy strategy) 
{ 
    this._strategy = strategy; 
} 

    // i may lose addtions to BaseObject doing this "downcasting" anyways? 
public void ContextInterface(BaseObject obj) 
{ 
    _strategy.DoSomething(obj); 
} 

} 
+0

+1 un tel scénario commun, j'ai vu des implémentations où obj ne cesse de croître et de plus en plus ... –

+0

Utiliser les interfaces des classes au lieu par exemple interface publique { void doSomething (objet BaseObject); } Ensuite, la stratégie héritera de cette interface. Basez votre SP autour de l'interface ou d'une inteface IStrategy qui hérite de cette interface.BTW utiliser DIP pour injection avec un IoC comme Ninject – GregJF

Répondre

13

Il semble que vous essayez réellement de réinventer le Visitor pattern, au lieu de simplement utiliser le modèle Stratégie comme il était prévu.

En outre, puisque vous utilisez C#, je vous recommande la lecture de l'article de Judith Bishop intitulé On the Efficiency of Design Patterns Implemented in C# 3.0. Cela couvre de multiples approches du modèle de visiteur en détail, et a quelques idées utiles intéressantes et connexes.

+0

Je convertis 2 formats de fichiers différents dans un format différent, si cela aide - je convertis les formats A et B à la fois C – user210757

+0

Une interface, avec une méthode ObjectC ConvertToC(), est probablement tout ce dont vous avez besoin, dans ce cas. Le format A et le format B (ou une classe qui fonctionne avec ces formats) ont juste besoin de mettre en œuvre cette interface, et vous avez terminé. –

+0

mais si vous voulez 2 méthodes - ObjectC ConvertToC (ObjectA a), ObjectC ConvertToC (ObjectB b), je pense que je aurais toujours le même problème – user210757

2

Le strategy pattern est destiné à fournir un comportement différent sur les objets d'entrée du même type.

Qu'est-ce que vous êtes en train d'essayer de faire est dépendant du contexte, et je ne suis pas sûr qu'il peut être vu à partir du code qui a été publié.

5

En C# signature de la méthode comprend son nom, la liste des paramètres de type et liste de paramètres formels. Dans le code ci-dessus "overrides" ont des signatures différentes de la méthode virtuelle et donc il n'est pas autorisé.

L'idée de base derrière modèle stratégie consiste à définir un ensemble d'algorithmes interchangeables avec des détails cachés à l'intérieur. Mais si vos stratégies diffèrent (par type) de ce qu'elles peuvent accepter en entrée, elles ne sont plus interchangeables. Donc, il semble que ce soit un mauvais modèle à utiliser dans cette situation.

0

Vous pouvez créer une classe de paramètres comme ceci:

public class Parameters 
{ 
    public ObjectA {get; set;} 
    public ObjectB {get; set;} 
} 

Le modifier vos méthodes pour accepter des paramètres tels que:

class StrategyA : Strategy 
{ 
public override void DoSomething(Parameters parameters) 
{ 
     // Now use ObjectA 
     if(parameters.ObjectA.SomeProperty == true) 
     { ... } 
} 
} 

De cette façon, vous pouvez les paramètres supplémentaires gré de vos exigences à l'avenir . Une autre alternative est d'utiliser Dictionary<string, object> où vous pouvez faire:

class StrategyA : Strategy 
{ 
    public override void DoSomething(Dictionary<string, object>parameters) 
    { 
      // Now use ObjectA 
      var someProperty = (bool)parameters["SomeProperty"]; 
      if() ... 
    } 
} 
4

Vous pouvez envisager cet article: http://hillside.net/plop/2010/papers/sobajic.pdf Le modèle est appelé « modèle de stratégie paramétrés » et doit correspondre à ce que vous avez besoin. Fondamentalement, il construit sur le modèle de stratégie et permet aux stratégies (différents algorithmes) d'avoir des paramètres différents. Les paramètres sont encapsulés dans des classes spéciales, c'est-à-dire des classes de paramètres. Chaque stratégie (c'est-à-dire l'algorithme) doit implémenter la méthode GetParameters() qui renvoie la liste des instances de parmaters pour un algorithme spécifique.

Questions connexes