为了理解委托,首先设计一个简单的业务场景
写一个简单的冒泡排序的算法
public int[]BubbleSort(int[] items)
{
objecttemp;
for(int i = items.Length - 1; i >= 0; i--)//从最后一个开始
{
for(int j = 1; j <= i; j++)
{
if(items[j - 1] > items[j])//如果比前一个数字大,就冒上去
{
temp = items[j - 1];
items[j - 1] =items[j];
items[j] = temp;
}
}
}
return items;
}
因为这个算法是一个经典算法,于是决定把他封装到一个通用的类库里,但是……,麻烦来了,如果传进去的变量是比对字符串怎么办?好,按照以前的思路,再加一个重载public static voidBubbleSort(string[] items),那如果我们遇到这样一个业务,拿到一些字符串,如 12564A,42344F,1234D,排序的规则是先比对最后一个字母,然后比对前面的4位数字,怎么办?也许以后还会遇到其它稀奇古怪的排序方式。我们这时发现,冒泡排序的算法是固定的,但是排序的比较方式是未知的。
好,当我们需要封装一个功能,但这个功能中其中有些内容是未知的,需要用户自定义时,这时委托可以上场了,这就是它的应用场景。
用这种方式,当有新的需求时,用户自己修改自定义的代码,而不必修改封装好的类,使得跨类边界调用耦合低。符合低耦合,高内聚,开放封闭原则。
既然委托能解决问题,那,我们看一下什么是委托。委托的本质就是一个指向方法的指针,可以让一个函数以参数的形式调用其它函数。
当然这个说法比较难以理解,我们一步一步来看,先看一看在C#里,委托这个“指针”是如何定义的,然后看一下什么叫“把一个以参数的形式”,最后看一看两个class之间的方法,如何通过委托发生关系。
1. 委托定义:public delegatebool CompareHandler(object obj1, objectobj2);相当于声明一个指针。
2. 以参数的形式:public object[]BubbleSort(object[] items, CompareHandler compareHalder){ ; }
3. 调用:
CommonMethod method = newCommonMethod();
method.BubbleSort(new object[] { "a", "m","d", "e"}, Compare);
private bool Compare(object obj1, objectobj2)
{
if(string.Compare(obj1.ToString(),obj2.ToString()) > 0)
{
returntrue;
}
else
{
returnfalse;
}
}
对于委托还有一种简化的写法,
delegate bool CompareHandler = delegate(object obj1, objectobj2)
{
if(string.Compare(obj1.ToString(),obj2.ToString()) > 0)
{
returntrue;
}
else
{
returnfalse;
}
如果代码看不明白,请运行附件源码(那个图片就是源码的压缩包,下载后把jpg的后缀改成rar就行了)。