我有一个名为Vector的类,我实现了乘法运算符,这是我的实现:
public static Object operator *(Vector x, Vector y)
{
//Possible return objects
Matrix multiplicationResultMatrix;
float multiplicationResultScalar = 0f;
if (x.VectorType != y.VectorType)
{
if (x.Length == y.Length)
{
if ((x.VectorType == VectorType.Row) && (y.VectorType == VectorType.Column))
{
for (ulong i = 0; i < x.Length; i++)
{
multiplicationResultScalar += x[i] * y[i];
}
}
else
{
if ((x.VectorType == VectorType.Column) && (y.VectorType == VectorType.Row))
{
multiplicationResultMatrix = new Matrix(x.Length);
for (ulong j = 0; j < x.Length; j++)
{
for (ulong i = 0; i < x.Length; i++)
{
multiplicationResultMatrix[i, j] += x[i] * y[j];
}
}
}
}
}
else
{
throw new ArithmeticException("Unhandled Arithmetic Exception, Multiplication of two vectors of different length is not allowed");
}
}
else
{
throw new ArithmeticException("Unhandled Arithmetic Exception, Multiplicating vectors of the same type is not allowed");
}
//What should I return
return ?
}
我应该如何定义返回类型?我考虑过装箱,并在消费时取消装箱,但我认为这不是一个安全的解决方案。
更新:
我还想过只返回一个矩阵对象,因为标量是1x1矩阵,问题是矩阵类得到了一些复杂的方法和特性,在1x1的情况下不能正常工作(这将迫使我添加一些代码),加上我想最小化和优化计算,我处理数百万的矩阵乘法。
答案 0 :(得分:5)
您应该避免根据输入参数的值更改返回类型(与编译时已知的静态类型相反)。这使得来电者可以完成您方法工作的一部分,即找出返回的内容。
有两种解决方案:
MultiplyRowCol
和MultiplyColRow
方法,返回不同类型的对象。从技术上讲,第一种解决方案更好,因为逐行乘法会产生一个带有单个元素的矩阵,而不是标量。
答案 1 :(得分:3)
C#对和类型的支持非常有限,但它是可能的。有一个nice implementation of a Discriminated Union here on StackOverFlow。使用此方法,您的方法可能如下所示:
public static Union2<Matrix, float> operator *(Vector x, Vector y)
{
(...)
return multiplicationResultMatrix != null
? new Union2<Matrix, float>.Case1(multiplicationResultMatrix)
: new Union2<Matrix, float>.Case2(multiplicationResultFloat);
}
请注意,我实际上并不建议在这种情况下执行此操作,因为我同意其他海报,总是返回矩阵会更好的设计。但你知道,这是可行的。
答案 2 :(得分:0)
如果他们没有共同的基类或接口,那么Object
是您唯一的选择。