/// <summary>
/// 动作基础类
/// </summary>
public abstract class ActionBase
{
/// <summary>
/// 动作名称
/// </summary>
public abstract string Name{ get;}
/// <summary>
/// 执行动作
/// </summary>
public abstract void Execute();
}
/// <summary>
/// 动作集合
/// </summary>
public class ActionList : System.Collections.CollectionBase
{
/// <summary>
/// 注册动作
/// </summary>
/// <param name="a"></param>
public void Registe( ActionBase a )
{
this.InnerList.Add( a );
}
/// <summary>
/// 获得指定名称的动作
/// </summary>
public ActionBase this[ string name ]
{
get
{
foreach( ActionBase a in this.InnerList )
{
if( a.Name == name )
return a ;
}
return null;
}
}
/// <summary>
/// 指定指定名称的动作
/// </summary>
/// <param name="name">动作名称</param>
public void Execute( string name )
{
ActionBase a = this[ name ];
if( a != null )
a.Execute();
}
}//public class ActionList : System.Collections.CollectionBase
internal class MyAction1 : ActionBase
{
public override string Name
{
get{ return "action1";}
}
public override void Execute()
{
System.Console.WriteLine( "Action1 execute");
}
}
internal class MyAction2 : ActionBase
{
public override string Name
{
get{ return "action2";}
}
public override void Execute()
{
System.Console.WriteLine( "Action2 execute");
}
}
public class StartApplication
{
public static void Main()
{
ActionList list = new ActionList();
list.Registe( new MyAction1());
list.Registe( new MyAction2());
list.Execute("action1");
}
}//public class StartApplication
/// 动作基础类
/// </summary>
public abstract class ActionBase
{
/// <summary>
/// 动作名称
/// </summary>
public abstract string Name{ get;}
/// <summary>
/// 执行动作
/// </summary>
public abstract void Execute();
}
/// <summary>
/// 动作集合
/// </summary>
public class ActionList : System.Collections.CollectionBase
{
/// <summary>
/// 注册动作
/// </summary>
/// <param name="a"></param>
public void Registe( ActionBase a )
{
this.InnerList.Add( a );
}
/// <summary>
/// 获得指定名称的动作
/// </summary>
public ActionBase this[ string name ]
{
get
{
foreach( ActionBase a in this.InnerList )
{
if( a.Name == name )
return a ;
}
return null;
}
}
/// <summary>
/// 指定指定名称的动作
/// </summary>
/// <param name="name">动作名称</param>
public void Execute( string name )
{
ActionBase a = this[ name ];
if( a != null )
a.Execute();
}
}//public class ActionList : System.Collections.CollectionBase
internal class MyAction1 : ActionBase
{
public override string Name
{
get{ return "action1";}
}
public override void Execute()
{
System.Console.WriteLine( "Action1 execute");
}
}
internal class MyAction2 : ActionBase
{
public override string Name
{
get{ return "action2";}
}
public override void Execute()
{
System.Console.WriteLine( "Action2 execute");
}
}
public class StartApplication
{
public static void Main()
{
ActionList list = new ActionList();
list.Registe( new MyAction1());
list.Registe( new MyAction2());
list.Execute("action1");
}
}//public class StartApplication
从上面的例子可以看出,实现一个可扩展结构需要很多类来支持。在很多情况下,我们只是需要简单的可扩展结构,而这种实现方式也太复杂臃肿了。
有时可以使用反射来实现简单的可扩展结构,例如微软.NET框架下的System.Xml.Xsl.XslTransform内部就使用了反射来实现对XSLT函数的扩展。但反射可能存在安全和性能问题,而且存在不方便调试的情况。
在此我提出使用委托来实现简单的可扩展结构。委托性能比反射好,安全而且便于调试。其例子为
/// <summary>
/// 定义委托类型
/// </summary>
public delegate void ActionMethodDelegate();
/// <summary>
/// 动作集合
/// </summary>
public class ActionList2
{
private System.Collections.Hashtable myTable = new System.Collections.Hashtable();
/// <summary>
/// 注册动作
/// </summary>
/// <param name="name">动作名称</param>
/// <param name="targe">方法</param>
public void Registe( string name , ActionMethodDelegate targe )
{
myTable[ name ] = targe ;
}
/// <summary>
/// 执行指定名称的动作
/// </summary>
/// <param name="name">动作名称</param>
public void Execute( string name )
{
ActionMethodDelegate targe = myTable[ name ] as ActionMethodDelegate ;
if( targe != null )
targe();
}
}
public class FunctionClass
{
public static void Action1()
{
System.Console.WriteLine( "Action1 execute");
}
public static void Action2()
{
System.Console.WriteLine("Action2 execute");
}
}
public class StartApplication2
{
public static void Main()
{
ActionList2 list = new ActionList2();
list.Registe( "action1" , new ActionMethodDelegate( FunctionClass.Action1 ));
list.Registe( "action2" , new ActionMethodDelegate( FunctionClass.Action2 ));
list.Execute( "action2");
}
}
/// 定义委托类型
/// </summary>
public delegate void ActionMethodDelegate();
/// <summary>
/// 动作集合
/// </summary>
public class ActionList2
{
private System.Collections.Hashtable myTable = new System.Collections.Hashtable();
/// <summary>
/// 注册动作
/// </summary>
/// <param name="name">动作名称</param>
/// <param name="targe">方法</param>
public void Registe( string name , ActionMethodDelegate targe )
{
myTable[ name ] = targe ;
}
/// <summary>
/// 执行指定名称的动作
/// </summary>
/// <param name="name">动作名称</param>
public void Execute( string name )
{
ActionMethodDelegate targe = myTable[ name ] as ActionMethodDelegate ;
if( targe != null )
targe();
}
}
public class FunctionClass
{
public static void Action1()
{
System.Console.WriteLine( "Action1 execute");
}
public static void Action2()
{
System.Console.WriteLine("Action2 execute");
}
}
public class StartApplication2
{
public static void Main()
{
ActionList2 list = new ActionList2();
list.Registe( "action1" , new ActionMethodDelegate( FunctionClass.Action1 ));
list.Registe( "action2" , new ActionMethodDelegate( FunctionClass.Action2 ));
list.Execute( "action2");
}
}
从上面的例子可以看出,使用委托来实现简单的可扩展结构,代码量和类的数量大大减少,而且扩展起来非常容易,只要实现某个静态函数,然后调用Registe函数注册一下就可以了。
对于有些按照名称调用功能的程序结构,一般的是使用switch-case结构来实现,现在可以考虑使用这种委托的可扩展结构,避免大型的switch-case语句,添加和删除功能比较方便,有利于函数的相互独立,而且便于扩展。
由于委托能接受参数,因此可以使用委托来实现稍微复杂的可扩展结构,但对于比较复杂功能强的可扩展结构,委托可能还不够,还得使用老办法。
XDesigner软件工作室( http://www.xdesigner.cn ) 2006-9-15