我偶然发现了一些类似于以下内容的代码:
if (myObject is MyClass1)
myOtherObject = new MyOtherClass1(myObject);
else if (myObject is MyClass2)
myOtherObject = new MyOtherClass2(myObject);
else if (myObject is MyClass3)
myOtherObject = new MyOtherClass3(myObject);
else if (myObject is MyClass4)
myOtherObject = new MyOtherClass4(myObject);
else if (myObject is MyClass5)
myOtherObject = new MyOtherClass5(myObject);
else if (myObject is MyClass6)
// ...
我发现这有点难以维护,并希望用不那么麻烦的东西来代替它。我有什么选择?
到目前为止,我已经考虑过使用字典的表驱动方法,但我不确定这是否是最佳选择。
// Not even sure this is valid syntax.
foreach (myClass in classes)
if myObject is myClass
new classes[myClass](myObject);
还有其他想法吗?
更新
这里没有详细介绍这些类的基本结构:
MyBaseClass MyOtherBaseClass
| |
-MyClass1 -MyOtherClass1
| |
-MyClass2 -MyOtherClass2
MyBaseClass及其后代是我认为的持久数据传输对象。它们以特定于类的格式存储数据。
我最接近描述MyOtherBaseClass及其后代的是单向数据映射器[PoEAA],但它们也混合了一些业务逻辑。
数据库仅包含足够的信息来定位对象并跟踪其状态。
答案 0 :(得分:5)
您是否可以考虑在generateOtherObject()
,MyClass1
等基类中使用抽象方法MyClass2
,在每个派生类中重写该方法以创建相关类型的新对象?
答案 1 :(得分:2)
另一个建议可能是使用构建器。
下面的一个依赖于Dictionary,对于每种类型,它描述了为生成新实例而执行的构建操作(应该比if-else / switch语句更容易维护)。
如果MyOtherClass1,MyOtherClass2全部来自MyOtherBaseClass
,则以下代码可以为您提供帮助:
public class YourTypeBuilderBuilder
{
private readonly static IDictionary<Type, Func<object, MyOtherBaseClass>> builderMap = new Dictionary<Type, Func<object, MyOtherBaseClass>>();
static YourTypeBuilderBuilder()
{
/* Here is described the specific behavior
of the building of the requested type */
builderMap.Add(typeof(MyClass1), obj => new MyOtherClass1((MyClass1)obj));
builderMap.Add(typeof(MyClass2), obj => new MyOtherClass2((MyClass2)obj));
builderMap.Add(typeof(MyClass3), obj => new MyOtherClass3((MyClass3)obj));
}
public static MyOtherBaseClass Build<T>(T input)
{
Func<object, MyOtherBaseClass> typeBuilder;
bool hasTypeBeenFound = builderMap.TryGetValue(typeof(T), out typeBuilder);
if (!hasTypeBeenFound)
{
throw new ArgumentException(string.Format("'{0}' is not a valid parameter.", typeof(T)));
}
// Let's build the requested type
MyOtherBaseClass obj = typeBuilder(input);
return obj;
}
}
然后您的调用代码将变为
myOtherObject = YourTypeBuilder.Build(myObject);