模板方法模式具有不同的实现方法参数
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了模板方法模式具有不同的实现方法参数相关的知识,希望对你有一定的参考价值。
我正在实现模板方法模式,在我的抽象类中,我有一个方法(TemplateMethod
)获取一些值并将它们传递给Step2
方法。
我遇到的冲突是我的两个具体实现仅使用这些参数的部分集合,因此我不喜欢传递所有参数的想法,如果另一个具体实现需要不同的参数,我不想修改此方法签名。
我读过关于Parameter Object模式并看到another very similar question in SO,但我仍然不相信。有什么建议?
这是我的简化代码:
void Main()
{
var concreteClassA = new ConcreteClassA();
concreteClassA.TemplateMethod();
var concreteClassB = new ConcreteClassB();
concreteClassB.TemplateMethod();
}
public abstract class AbstractClass
{
IEngine1 _engine1;
IEngine2 _engine2;
public void TemplateMethod() {
Step1();
//Get some values
var id = _engine1.GetId();
var name = _engine1.GetName();
var anotherId = _engine2.GetAnotherId();
var description = _engine2.GetDescription();
//Pass all values to step 2
Step2(id, name, anotherId, description);
}
public virtual void Step1() { }
public virtual void Step2(int id, string name, int anotherId, int description) {}
}
public interface IEngine1 {
int GetId();
string GetName();
}
public interface IEngine2
{
int GetAnotherId();
int GetDescription();
}
public class ConcreteClassA : AbstractClass
{
public override void Step2(int id, string name, int anotherId, int description)
{
//This class only needs Id and name!
var entity = new Entity {
Id = id,
Name = name
}
DoSomethingWithEntity(entity);
}
private void DoSomethingWithEntity(Entity entity) {
//Logic here
}
}
public class ConcreteClassB : AbstractClass
{
public override void Step2(int id, string name, int anotherId, int description)
{
//This one needs other parameters
var entity = new Entity
{
AnotherId = anotherId,
Name = name,
Description = description
}
DoSomethingElseWithEntity(entity);
}
private void DoSomethingElseWithEntity(Entity entity)
{
//Logic here
}
}
public class Entity {
public int Id { get; set; }
public string Name { get; set; }
public int AnotherId { get; set; }
public int Description { get; set;}
}
答案
您可以尝试传递模型。您只需将模型作为参数即可
当您将更改参数时,不会更改Step2
方法签名。
只需在ParamterContext
添加房产
这是示例代码
public class ParameterContext
{
public int id { get; set; }
public string name { get; set; }
public int anotherId { get; set; }
public int description { get; set; }
}
public abstract class AbstractClass
{
IEngine1 _engine1;
IEngine2 _engine2;
public void TemplateMethod()
{
Step1();
//Get some values
var id = _engine1.GetId();
var name = _engine1.GetName();
var anotherId = _engine2.GetAnotherId();
var description = _engine2.GetDescription();
//Pass all values to step 2
Step2(new ParameterContext() {
id = id,
name = name,
anotherId = anotherId,
description = description
});
}
public virtual void Step1() { }
public virtual void Step2(ParameterContext parameter) { }
}
public interface IEngine1
{
int GetId();
string GetName();
}
public interface IEngine2
{
int GetAnotherId();
int GetDescription();
}
public class ConcreteClassA : AbstractClass
{
public override void Step2(ParameterContext para)
{
//This class only needs Id and name!
var entity = new Entity
{
Id = para.id,
Name = para.name
};
DoSomethingWithEntity(entity);
}
private void DoSomethingWithEntity(Entity entity)
{
//Logic here
}
}
public class ConcreteClassB : AbstractClass
{
public override void Step2(ParameterContext para)
{
//This one needs other parameters
var entity = new Entity
{
AnotherId = para.anotherId,
Name = para.name,
Description = para.description
};
DoSomethingElseWithEntity(entity);
}
private void DoSomethingElseWithEntity(Entity entity)
{
//Logic here
}
}
编辑
另一种方式是
IEngine1
和IEngine2
接口声明为保护,在AbstractClass
类中,您可以使用他们的方法而不是传递参数。
public abstract class AbstractClass
{
public AbstractClass() { }
public AbstractClass(IEngine1 eng1, IEngine2 eng2)
{
_engine1 = eng1;
_engine2 = eng2;
}
protected IEngine1 _engine1;
protected IEngine2 _engine2;
public void TemplateMethod()
{
Step1();
//Get some values
//var id = _engine1.GetId();
//var name = _engine1.GetName();
//var anotherId = _engine2.GetAnotherId();
//var description = _engine2.GetDescription();
//Pass all values to step 2
Step2();
}
public virtual void Step1() { }
public virtual void Step2() { }
}
public interface IEngine1
{
int GetId();
string GetName();
}
public interface IEngine2
{
int GetAnotherId();
int GetDescription();
}
public class ConcreteClassA : AbstractClass
{
public override void Step2()
{
//This class only needs Id and name!
var entity = new Entity
{
Id = _engine1.GetId(),
Name = _engine1.GetName()
};
DoSomethingWithEntity(entity);
}
private void DoSomethingWithEntity(Entity entity)
{
//Logic here
}
}
public class ConcreteClassB : AbstractClass
{
public override void Step2()
{
//This one needs other parameters
var entity = new Entity
{
AnotherId = _engine2.GetAnotherId(),
Name = _engine1.GetName(),
Description = _engine2.GetDescription()
};
DoSomethingElseWithEntity(entity);
}
private void DoSomethingElseWithEntity(Entity entity)
{
//Logic here
}
}
public class Entity
{
public int Id { get; set; }
public string Name { get; set; }
public int AnotherId { get; set; }
public int Description { get; set; }
}
以上是关于模板方法模式具有不同的实现方法参数的主要内容,如果未能解决你的问题,请参考以下文章