以非泛型方式调用泛型方法(三)
原创
©著作权归作者所有:来自51CTO博客作者obarton的原创作品,请联系作者获取转载授权,否则将追究法律责任
结论:
以下是测试代码:
using System;
using System.Collections.Generic;
using System.Reflection;
using System.Text;
![以非泛型方式调用泛型方法(三)_休闲](http://www.cnblogs.com/Images/OutliningIndicators/None.gif)
namespace GenericMethodTest
![以非泛型方式调用泛型方法(三)_休闲_07](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedBlockStart.gif)
![以非泛型方式调用泛型方法(三)_休闲_08](http://www.cnblogs.com/Images/OutliningIndicators/ContractedBlock.gif)
{
// 为泛型方法定义的委托
public delegate void GM<T>(T obj, IList<T> list);
![以非泛型方式调用泛型方法(三)_休闲_10](http://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
// 为非泛型方法定义的接口
public interface ING
![以非泛型方式调用泛型方法(三)_泛型_15](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
void NGM(object obj, object list);
}
![以非泛型方式调用泛型方法(三)_休闲_10](http://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
class Program
![以非泛型方式调用泛型方法(三)_泛型_22](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
static void Main(string[] args)
![以非泛型方式调用泛型方法(三)_休闲_26](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
List<int> list = new List<int>();
System.Diagnostics.Stopwatch watch = new System.Diagnostics.Stopwatch();
watch.Reset();
watch.Start();
for (int i = 0; i < 1000000; i++)
![以非泛型方式调用泛型方法(三)_职场_34](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
list.Add(i);
}
watch.Stop();
long l1 = watch.ElapsedMilliseconds;
watch.Reset();
watch.Start();
GM<int> gm = new GM<int>(Program.Add);
for (int i = 0; i < 1000000; i++)
![以非泛型方式调用泛型方法(三)_职场_45](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
gm(i, list);
}
watch.Stop();
long l2 = watch.ElapsedMilliseconds;
watch.Reset();
watch.Start();
MethodInfo mi = typeof(Program).GetMethod("Add");
MethodInfo gmi = mi.MakeGenericMethod(typeof(int));
for (int i = 0; i < 1000000; i++)
![以非泛型方式调用泛型方法(三)_休闲_57](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
![以非泛型方式调用泛型方法(三)_职场_60](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
gmi.Invoke(null, new object[]
{ i, list });
}
watch.Stop();
long l3 = watch.ElapsedMilliseconds;
watch.Reset();
watch.Start();
ING ng1 = GetNGC(typeof(int), typeof(Program), "Add");
for (int i = 0; i < 1000000; i++)
![以非泛型方式调用泛型方法(三)_休闲_70](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
ng1.NGM(i, list);
}
watch.Stop();
long l4 = watch.ElapsedMilliseconds;
watch.Reset();
watch.Start();
ING ng2 = InterfaceGenerator.GetInterface<ING>(new GM<int>(Program.Add));
for (int i = 0; i < 1000000; i++)
![以非泛型方式调用泛型方法(三)_泛型_81](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
ng2.NGM(i, list);
}
watch.Stop();
long l5 = watch.ElapsedMilliseconds;
Console.WriteLine("{0}\n{1} vs {2} vs {3} vs {4} vs {5}", list.Count, l1, l2, l3, l4, l5);
Console.ReadLine();
}
![以非泛型方式调用泛型方法(三)_休闲_10](http://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
public static void Add<T>(T obj, IList<T> list)
![以非泛型方式调用泛型方法(三)_泛型_93](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
list.Add(obj);
}
![以非泛型方式调用泛型方法(三)_休闲_10](http://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
static ING GetNGC(Type genericType, Type methodType, string methodName)
![以非泛型方式调用泛型方法(三)_泛型_100](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
MethodInfo mi = methodType.GetMethod(methodName);
MethodInfo gmi = mi.MakeGenericMethod(genericType);
Delegate gmd = Delegate.CreateDelegate(typeof(GM<>).MakeGenericType(genericType), gmi);
return Activator.CreateInstance(typeof(GClass<>).MakeGenericType(genericType), gmd) as ING;
}
}
![以非泛型方式调用泛型方法(三)_休闲_10](http://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
public class GClass<T> : ING
![以非泛型方式调用泛型方法(三)_职场_111](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
private GM<T> m_gmd;
![以非泛型方式调用泛型方法(三)_休闲_10](http://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
public GClass(GM<T> gmd)
![以非泛型方式调用泛型方法(三)_泛型_117](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
m_gmd = gmd;
}
![以非泛型方式调用泛型方法(三)_休闲_10](http://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
![以非泛型方式调用泛型方法(三)_休闲_123](http://www.cnblogs.com/Images/OutliningIndicators/ContractedSubBlock.gif)
INGClass 成员#region INGClass 成员
![以非泛型方式调用泛型方法(三)_休闲_10](http://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
public void NGM(object obj, object list)
![以非泛型方式调用泛型方法(三)_职场_127](http://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
m_gmd((T)obj, (IList<T>)list);
}
![以非泛型方式调用泛型方法(三)_休闲_10](http://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
#endregion
}
}
![以非泛型方式调用泛型方法(三)_休闲](http://www.cnblogs.com/Images/OutliningIndicators/None.gif)
测试结果:
方案 |
耗时 |
比对 |
其他优点 |
直接调用 |
18 |
1 |
不通用 |
泛型委托包装 |
43 |
2.39 |
不通用 |
反射 |
16538 |
918.78 |
通用,不需额外定义 |
非泛型接口包装 |
60 |
3.33 |
通用,需要额外定义并实现 |
动态生成的非泛型接口包装 |
72 |
4 |
通用,需要额外定义 |