前言 :
面向对象设计守则里有一条:多用合成,少用继承。
面向对象设计守则的内容可以参考,
[深入浅出设计模式] : http://www.oreilly.com.tw/product_java.php?id=a163
本篇文章示范如何实作界面、抽象类的抽象合成,让合成之后的类别依然保有抽象方法。
使用时机 :
当有一堆抽象类,想要集合成一个大的抽象类时使用。
例如说
现在要实作Facade这个模式 可是有些抽象对象的方法,要让使用者去实作。 这个时候,抽象合成就可以派上用场。
结构 :
实作 :
首先先要有一个抽象类
public abstract class Strategy
{
public int ClassMethod001(string x)
{
return int.Parse(x);
}
public abstract string ClassMethod002(int x);
}
再来就是抽象类的合成类别
public abstract class Context
{
// Properties
private Strategy _strategy = null;
// Constructor
public Context()
{
// Agent
_strategy = new StrategyAgent(this.ClassMethod002);
}
// Methods
public int ClassMethod001(string x)
{
return _strategy.ClassMethod001(x);
}
public abstract string ClassMethod002(int x);
// Class
private class StrategyAgent : Strategy
{
// Delegate
public delegate string ClassMethod002Delegate(int x);
// Properties
private ClassMethod002Delegate _classMethod002Delegate = null;
// Constructor
public StrategyAgent(ClassMethod002Delegate classMethod002Delegate)
{
#region Require
if (classMethod002Delegate == null) throw new ArgumentNullException();
#endregion
_classMethod002Delegate = classMethod002Delegate;
}
// Methods
public override string ClassMethod002(int x)
{
return _classMethod002Delegate(x);
}
}
}
最后我们就可以继承合成类别,来达成继承被合成抽象类的工作。
public class ContextA : Context
{
public override string ClassMethod002(int x)
{
return x.ToString("D3");
}
}
public class ContextB : Context
{
public override string ClassMethod002(int x)
{
return x.ToString("X2");
}
}
执行
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
ContextA contextA = new ContextA();
Console.WriteLine(contextA.ClassMethod001("255"));
Console.WriteLine(contextA.ClassMethod002(255));
Console.WriteLine();
ContextB contextB = new ContextB();
Console.WriteLine(contextB.ClassMethod001("255"));
Console.WriteLine(contextB.ClassMethod002(0xFF));
Console.ReadLine();
}
}
}
