C# 为什么是;式中T:class";本例中是否需要?

C# 为什么是;式中T:class";本例中是否需要?,c#,.net,generics,filehelpers,C#,.net,Generics,Filehelpers,示例代码: using System.Collections.Generic; using FileHelpers; .... private void Save<T>(string destFilename, IEnumerable<T> data) where T : class { var engine = new FileHelperEngine((typeof(T))); engine.HeaderText = engine.Ge

示例代码:

using System.Collections.Generic;
using FileHelpers;

....
private void Save<T>(string destFilename,  IEnumerable<T> data) where T : class    
{
    var engine = new FileHelperEngine((typeof(T)));


    engine.HeaderText = engine.GetFileHeader(); 
    engine.WriteFile(destFilename, data); // XX
}
使用System.Collections.Generic;
使用文件助手;
....
私有void保存(字符串destFilename,IEnumerable数据),其中T:class
{
var engine=newfilehelperengine((typeof(T));
engine.HeaderText=engine.GetFileHeader();
engine.WriteFile(destFilename,data);//XX
}
在第XX行,engine.WriteFile的第二个参数应为IEnumerable。这个代码工作正常

我的问题是,为什么方法上需要“where T:class”约束?如果删除它,则会出现编译时错误:

Argument 2: cannot convert from
'System.Collections.Generic.IEnumerable<T>' to
'System.Collections.Generic.IEnumerable<object>'
参数2:无法从转换
“System.Collections.Generic.IEnumerable”到
'System.Collections.Generic.IEnumerable'

我会认为一切都是一个“对象”,所以约束是不必要的

需要约束,因为
对象
仅为引用类型;之所以可以将值类型指定给
对象
,是因为装箱(尽管从技术上讲,所有类型都继承自
System.object

但装箱与类型参数差异是一个单独的问题;带有无约束T的
IEnumerable
无法转换为
IEnumerable
,因为值类型不支持方差

另一方面,非泛型的
FileHelperEngine
继承自的
FileHelperEngine
,也有一个
T:class
约束。因此,由于只支持引用类型,因此使用约束不会丢失任何功能-理论上可以直接使用
FileHelperEngine
,而不必经过非泛型类,因为示例中给出的方法已经是泛型的:

using System.Collections.Generic;
using FileHelpers;

....
private void Save<T>(string destFilename,  IEnumerable<T> data) where T : class    
{
    var engine = new FileHelperEngine<T>();


    engine.HeaderText = engine.GetFileHeader(); 
    engine.WriteFile(destFilename, data);
}
使用System.Collections.Generic;
使用文件助手;
....
私有void保存(字符串destFilename,IEnumerable数据),其中T:class
{
var engine=new FileHelperEngine();
engine.HeaderText=engine.GetFileHeader();
engine.WriteFile(文件名、数据);
}

您要将
T
应用于
FileHelperEngine
,它已经具有相同的约束,
T:class
。编译器可以告诉您,如果您没有对方法施加相同的约束,则
t
可能对
FileHelperEngine
无效。
所以这只是为了防止类型不匹配。

谢谢。另外,关于FileHelpers的最后一段也很好,如果您使用FileHelperEngine,就像BoltClock的示例一样,这是正确的。但在使用FIleHelperEngine(类型recordType)时,情况似乎与我最初的示例不同。