Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/332.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/.net/21.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 更多琐事而不是真正重要的:为什么Activator.CreateInstance上没有新的()约束<;T>;()?_C#_.net_Clr_C# 2.0_Base Class Library - Fatal编程技术网

C# 更多琐事而不是真正重要的:为什么Activator.CreateInstance上没有新的()约束<;T>;()?

C# 更多琐事而不是真正重要的:为什么Activator.CreateInstance上没有新的()约束<;T>;()?,c#,.net,clr,c#-2.0,base-class-library,C#,.net,Clr,C# 2.0,Base Class Library,我认为有人可能能够回答这个问题,这是一个出于好奇的问题: .NET v2中引入的System.Activator中的泛型CreateInstance方法对泛型参数没有类型约束,但需要对激活的类型使用默认构造函数,否则会引发MissingMethodException。对我来说,这个方法显然应该有一个类型约束,比如 Activator.CreateInstance<T>() where T : new() { ... } Activator.CreateInstance(),其

我认为有人可能能够回答这个问题,这是一个出于好奇的问题:

.NET v2中引入的
System.Activator
中的泛型
CreateInstance
方法对泛型参数没有类型约束,但需要对激活的类型使用默认构造函数,否则会引发
MissingMethodException
。对我来说,这个方法显然应该有一个类型约束,比如

Activator.CreateInstance<T>() where T : new() {
   ...
}
Activator.CreateInstance(),其中T:new(){
...
}
只是一个遗漏或一些隐藏在这里的轶事

更新

如前所述,编译器不允许您编写

private T Create<T>() where T : struct, new()
error CS0451: The 'new()' constraint cannot be used with the 'struct' constraint
private T Create(),其中T:struct,new()
错误CS0451:“new()”约束不能与“struct”约束一起使用
但是,请参见注释:结构可以用作指定新()约束的泛型方法的类型参数。在这种情况下,给出的答案似乎是不限制该方法的唯一有效理由


谢谢你看这个

我可能错了,但在我看来,它的主要好处是允许您执行以下操作:

// Simple illustration only, not claiming this is awesome code!
class Cache<T>
{
    private T _instance;

    public T Get()
    {
        if (_instance == null)
        {
            _instance = Create();
        }

        return _instance;
    }

    protected virtual T Create()
    {
        return Activator.CreateInstance<T>();
    }
}
//仅作简单说明,不声称这是一个很棒的代码!
类缓存
{
私人T_实例;
公共部门得不到
{
if(_instance==null)
{
_instance=Create();
}
返回_实例;
}
受保护的虚拟T创建()
{
返回Activator.CreateInstance();
}
}

请注意,如果
Activator.CreateInstance
具有
where T:new()
约束,则上面的
缓存
类也将需要该约束,这将是过度限制的,因为
Create
是一个虚拟方法,某些派生类可能希望使用不同的实例化方法,例如调用类型的内部构造函数或使用静态生成器方法。

+1非常有趣的问题。我想不出为什么它不应该在那里,所以我也想知道为什么!至于你的更新,因为它是多余的;所有值类型都有一个默认构造函数,它将所有值初始化为默认值(这是调用
default(T)
时得到的。所有结构都有C#中的默认构造函数。请澄清,给定
void Foo(),其中T:new(){}
Foo();
Foo()
都是编译器不会抱怨的完全有效的调用。问题很好。我感到困惑。
新的
约束似乎是与泛型同时引入的,所以这不像是向后兼容性问题。也许他们只是忘记了?+1。这是一个很好的观点。尽管你承担了一些风险(显然,
T
可能没有默认构造函数),这似乎是一个完全有效的例子。顺便说一句,它看起来像
System.Runtime.CompilerServices.ConditionalWeakTable
做了这件事。还值得注意的是
CreateInstance
方法受
的约束,其中T:new()
将是完全冗余的。由于编译时必须知道
T
,因此可以使用
var x=new T()创建受
where T:new()约束的任何
T
语法。@LukeH:Ha,是的,这是一个有趣的问题,而如果
Activator.CreateInstance
确实有
where T:new()
约束,那么肯定会有一个问题,“Activator.CreateInstance
到底有什么意义?”@Dan,LukeH:值得一提的是,对
new T()
的调用实际上变成了对
Activator.CreateInstance()的调用。