2011-11-15 34 views
14

实施例1(不编译):懒惰<T>如何解决需要new()约束?

void Main() 
{ 
    var c = new C<D>(); 
    c.M.F(); 
} 

class C<T> 
{ 
    T _m = null; 
    public T M { get { 
     if(_m == null) _m = new T(); 
     return _m; 
    } } 
} 

class D 
{ 
    public void F() { Console.WriteLine ("i was created"); } 
} 

结果:

,因为它不具有new()约束

无法创建变量类型 'T' 的一个实例

实施例2(作品):

void Main() 
{ 
    var c = new C<D>(); 
    c.M.F(); 
} 

class C<T> 
{ 
    Lazy<T> _m = new Lazy<T>(); 
    public T M { get { return _m.Value; } } 
} 

class D 
{ 
    public void F() { Console.WriteLine ("i was created"); } 
} 

Resul T:

i was created 

回答

17

如果你深入到源代码,你会看到Lazy<T>最终使用Activator

return new Lazy<T>.Boxed((T)Activator.CreateInstance(typeof(T))); 

这仅仅是使用反射的快捷方式。由于它不是通过实际泛型类型参数(new T())实例化类型,而是通过反射调用构造函数,因此不需要where T : new()约束。