如何用泛型类的不同泛型类型的操作数重载泛型类的运算符
本文关键字:泛型类 操作数 重载 运算符 泛型类型 何用 | 更新日期: 2023-09-27 18:28:17
有很多类似的问题,但都涉及相同类型或相同泛型类型的操作数。特别是这一个(如何使用带有运算符重载的泛型类型参数?)与我想要的很接近,但没有答案或解决方法。
有可能对"*"操作员过载做这样的事情吗:
public class MyNumericClass<T>
{
public double Value { get; set; }
//OK but works only for same type operands
public static double operator *(MyNumericClass<T> left, MyNumericClass<T> right)
{
return left.Value * right.Value;
}
//****Pseudo Code for different type operands - not OK****
public static double operator *<TRight>(MyNumericClass<T> left, MyNumericClass<TRight> right)
{
return left.Value * right.Value;
}
static void Test()
{
MyNumericClass<int> i = new MyNumericClass<int>();
MyNumericClass<int> j = new MyNumericClass<int>();
MyNumericClass<string> s = new MyNumericClass<string>();
double r1 = i * j;
double r2 = i * s; //Operator '*' cannot be applied to operands...
}
}
我需要为不同的泛型类型指定一个特定的重载。在这种情况下,非泛型超类不会起作用,因为我有其他运算符重载(此处未显示),如果我使用超类类型的参数而不是确切的泛型类型,则会产生不明确的调用。
有可能做到这一点吗?或者周围有工作吗?是否可以使用op_Multiply?(试过了,但没能成功)。
附言:我看不出有什么理由不可能发生这样的事情。
编辑1在人们的回答和评论之后,我添加了另一个版本的类,其中包含隐式类型转换和更多重载,以演示调用的模糊性,以及为什么提供的答案不能解决我的问题。我需要在我的运算符重载中指定不同的泛型类型来解决这个问题:
public class MyNumericClass<T>
{
public double Value { get; set; }
public static implicit operator double(MyNumericClass<T> value)
{
return value.Value;
}
public static implicit operator MyNumericClass<T>(double value)
{
MyNumericClass<T> c = new MyNumericClass<T>();
c.Value = value;
return c;
}
public static MyNumericClass<T> operator *(double left, MyNumericClass<T> right)
{
return left * right.Value;
}
public static MyNumericClass<T> operator *(MyNumericClass<T> left, double right)
{
return right * left;
}
//Does not resolve ambiguity and neither does a base class or interface
public static double operator *(MyNumericClass<T> left, dynamic right)
{
return right * left;
}
//OK but work only for same type operands
public static double operator *(MyNumericClass<T> left, MyNumericClass<T> right)
{
return left.Value * right.Value;
}
////****Pseudo Code for different type operands - not OK****
//public static double operator *<TRight>(MyNumericClass<T> left, MyNumericClass<TRight> right)
//{
// return left.Value * right.Value;
//}
static void Test()
{
MyNumericClass<int> i = new MyNumericClass<int>();
MyNumericClass<int> j = new MyNumericClass<int>();
MyNumericClass<string> s = new MyNumericClass<string>();
double r1 = i * j;
double r2 = i * s; //The call is ambiguous...
}
}
这实际上取决于您将来希望如何使用它
您可以:
制作一个包含Value的非泛型基类。然后,操作符处理基类。
实现接口并使用协方差。
像这样:
void Main()
{
MyNumericClass<int> i = new MyNumericClass<int>();
MyNumericClass<int> j = new MyNumericClass<int>();
MyNumericClass<string> s = new MyNumericClass<string>();
double r1 = i * j;
double r2 = i * s;
}
public interface IMyNumericClass<out T> {
double Value { get; set; }
}
public class MyNumericClass<T> : IMyNumericClass<T>
{
public double Value { get; set; }
public static double operator *(MyNumericClass<T> left, MyNumericClass<T> right)
{
return left.Value * right.Value;
}
public static double operator *(MyNumericClass<T> left, IMyNumericClass<object> right)
{
return left.Value * right.Value;
}
}
您可能需要像这样做
public class MyNumericClass<T>
{
public double Value { get; set; }
//OK but works only for same type operands
public static double operator *(MyNumericClass<T> left, MyNumericClass<double> right)
{
return left.Value * right.Value;
}
public static double operator *(MyNumericClass<T> left, MyNumericClass<T> right)
{
return left.Value * right.Value;
}
static void Test()
{
MyNumericClass<int> i = new MyNumericClass<int>();
MyNumericClass<int> i2 = new MyNumericClass<int>();
MyNumericClass<double> j = new MyNumericClass<double>();
double r1 = i * i2;
double r2 = i * j;
}
}