泛型用于将逻辑与数据类型分离。
public class Calc<T>
{
public T Add(T a, T b)
{
return (a+b);
}
}
但是这会抛出以下编译时错误
操作员+无法应用于T类型。
我不明白为什么会这样。因为如果它允许来自main.cs
main()
{
Calc<int> obj = new Calc<int>();
int c = obj.Add(10,20);
}
有人可以解释为什么我会收到Build错误吗?
答案 0 :(得分:2)
C#泛型不支持任意运算符。必须在泛型类型的编译时中知道确切的(可能是虚拟的)方法。由于示例中的泛型类型参数根本不受约束,因此您只能使用object
类型的成员,该成员不包含+
运算符。
没有办法使用C#generics来做你想做的事,抱歉。您可以做的最好的事情是对一些已知类型的一系列类型检查(以及适当的强制转换,对于值类型来说很棘手),或者使用反射(dynamic
特别适用)。
答案 1 :(得分:1)
像Calc<T>
这样的不受限制的泛型必须能够使用任何类型进行编译,并非所有类型都支持+
操作数,因此您的代码无法编译。这与您使用。
您可以限制T
的类型,从而通过Calc<T> where T:object
或Calc<T> where T: IComparable
访问更多方法,这样您就可以:
public T CompareTo(T a, T b)
{
return (a.CompareTo(b));
}
由于所有T
现在必须实施IComparable
。遗憾的是,Int32
未实现任何定义+
运算符或任何添加方法的接口。所以没有办法实现你正在尝试的那个陈述。
答案 2 :(得分:0)
C#泛型与C ++模板不同。如果泛型类型没有使用used方法的定义(在你的情况下是operator +),则无法编译C#代码,而C ++编译器将此方法应用于实际的模板参数类型。
答案 3 :(得分:0)
不允许添加,因为无法保证传递的类型具有operator + overload
有一种方法可以实现,但只要您传递具有operator +的类型,它就会起作用。否则,将抛出RuntimeBinderException
。此外,对性能有一些影响,但除非代码对性能至关重要,否则不应该成为问题。
public T Add<T>(T a, T b)
{
dynamic da = a, db = b;
return da + db;
}