操作员评估期间的C#动态铸造

本文关键字:动态 评估 操作员 | 更新日期: 2023-09-27 18:26:08

我目前有一个用户定义的类型

class MyType {
    double x;
    double y;
    double z;
    //This class has operator overloading implemented
    public static MyType operator + (double a,MyType b){
        ...
    }
}

稍后我会有一个数组(object[]),其中一些是double,还有一些是MyType。我想对它们进行求值,但编译器不允许将运算符"+"应用于类型对象和对象。我在这里该怎么办?

操作员评估期间的C#动态铸造

解析代码中的+时,编译器需要将其绑定到特定操作。类型object没有+操作,编译器不知道底层类型是doubleMyType,因此编译器出错。

为了解决这个问题,您需要使用

  • 静态地将元素转换为doubleMyType,这样编译器就可以正确地绑定+运算符
  • 使用CCD_ 9并且依赖于到正确的CCD_

下面是后一种方法的例子。

class MyType {
    double _value;
    internal MyType(double value) {
        _value = value;
    }
    public static MyType operator +(double left, MyType right) {
        return new MyType(left + right._value);
    }
    public static MyType operator +(MyType left, double right) {
        return new MyType(left._value + right);
    }
    public static MyType operator +(MyType left, MyType right) {
        return new MyType(left._value + right._value);
    }
    public static implicit operator MyType(double other) {
        return new MyType(other);
    }
}
class Program
{
    static void Main(string[] args) {
        object[] them = new object[] {
            42,
            new MyType(13),
            12,
            new MyType(12)
        };
        dynamic all = them;
        MyType sum = 0;
        foreach (dynamic element in all) {
            sum += element;
        }
        Console.WriteLine(sum);
    }
}

老实说,我会创建一个采用单个double参数的MyType构造函数,并使用它将每个double转换为MyType,这样您就可以只使用MyType[](或List<MyType>)。

我知道这确实不是您所要求的,但您仍然可以处理MyType的创建,这样添加就可以正常执行,并且您的数组的类型更加安全。

您应该更具体地处理您的类型-您不能添加的原因是对象可能是系统中的任意对象。

有什么方法可以将对象更改为更特定的类型吗?

如果它绝对必须是对象,那么您将不得不在运行时使用强制转换或as运算符或一些类似的机制进行计算。

例如

    public static MyType operator +(object o, MyType b)
    {
        MyOtherType mot = o as MyOtherType;
        if(o!=null)
            ...

但毫无疑问,您在这里的解决方案会对您的设计选择提出疑问