我在C#2010中读到了类型dynamic
。(相应的msdn条目)
在开发通用函数时,我对T
和dynamic
之间的实际区别感到困惑。我目前的测试没有显示使用dynamic
方式的新方法,这对于T
是不可能的。此外,似乎动态需要更多的时间在运行时才能完成相同的任务。
一些示例代码使我的观点清楚:
// Sample Object
public class SampleObj
{
public string Test { get; set; }
}
我的测试方法(测量速度以及):
static void Main(string[] args)
{
var sampleObj1 = new SampleObj { Test = "Test1" };
var sampleObj2 = new SampleObj { Test = "Test2" };
Stopwatch c1 = Stopwatch.StartNew();
bool res1 = CompareObjectsT<SampleObj>(sampleObj1, sampleObj2);
c1.Stop();
Console.WriteLine("Comparison T: {0} time: {1} ms", res1, c1.ElapsedMilliseconds);
Stopwatch c2 = Stopwatch.StartNew();
bool res2 = CompareObjectsDyna(sampleObj1, sampleObj2);
Console.WriteLine("Comparison dynamic: {0} time: {1} ms", res2, c2.ElapsedMilliseconds);
c2.Stop();
var instance = new X<SampleObj>();
Console.ReadLine();
}
结果是:
Comparison T: False time: 6 ms
Comparison dynamic: False time: 3969 ms
与T比较相比,动态函数需要多更多时间。
反编译我的测试应用程序会发现反射的大量使用可能会导致这么长的时间:
private static bool CompareObjectsDyna([Dynamic] object source1, [Dynamic] object source2)
{
if (<CompareObjectsDyna>o__SiteContainer2.<>p__Site3 == null)
{
<CompareObjectsDyna>o__SiteContainer2.<>p__Site3 = CallSite<Func<CallSite, object, bool>>.Create(Binder.Convert(CSharpBinderFlags.None, typeof(bool), typeof(Program)));
}
if (<CompareObjectsDyna>o__SiteContainer2.<>p__Site4 == null)
{
<CompareObjectsDyna>o__SiteContainer2.<>p__Site4 = CallSite<Func<CallSite, Type, object, object, object>>.Create(Binder.InvokeMember(CSharpBinderFlags.None, "Equals", null, typeof(Program), new CSharpArgumentInfo[] { CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.IsStaticType | CSharpArgumentInfoFlags.UseCompileTimeType, null), CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null), CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null) }));
}
return <CompareObjectsDyna>o__SiteContainer2.<>p__Site3.Target(<CompareObjectsDyna>o__SiteContainer2.<>p__Site3, <CompareObjectsDyna>o__SiteContainer2.<>p__Site4.Target(<CompareObjectsDyna>o__SiteContainer2.<>p__Site4, typeof(object), source1, source2));
}
我考虑过this post,但这并没有提出我的问题。
有人能告诉我,在什么情况下动态比T更有效? (希望有一个小的实际样本)
答案 0 :(得分:4)
简短回答是通用类型T必须在编译时知道,但动态是在运行时推断的。