立即为所有原始数字数据类型实现运算符覆盖/Equatable<T>?

我想实现我自己的 CustomNumber 类,并使用关系运算符将其与所有其他原始数字数据类型(int、long、double、float 等)进行比较。

有没有办法同时对所有这些操作符执行此操作,或者我真的必须重写 ==、!=、>、<、>= 和 <= 运算符以及每个单个操作符的 Equals(T other) 方法整数数据类型?

我想我知道运算符重载一般是如何工作的,但感觉必须有某种快捷方式才能使我的 CustomNumber 与使用关系运算符的所有原始数字数据类型进行比较,而不是必须为每个运算符重载这 6 个运算符中的每一个单一数据类型,可能很快就会添加大约 100 个重载定义。


拉丁的传说
浏览 70回答 2
2回答

慕森卡

本身没有捷径,您必须为您想要支持的所有类型实现所有运算符和功能,它无法读懂您的想法。检查decimal 实施情况。为了您的理智,您会注意到并非所有内容都需要被覆盖,这是通过隐式运算符的实现来完成的:public static implicit operator Decimal(byte value){   return new Decimal(value);}[CLSCompliant(false)]public static implicit operator Decimal(sbyte value){   return new Decimal(value);}public static implicit operator Decimal(short value){   return new Decimal(value);}[CLSCompliant(false)]public static implicit operator Decimal(ushort value){   return new Decimal(value);}public static implicit operator Decimal(char value){   return new Decimal(value);}public static implicit operator Decimal(int value){   return new Decimal(value);}[CLSCompliant(false)]public static implicit operator Decimal(uint value){   return new Decimal(value);}public static implicit operator Decimal(long value){   return new Decimal(value);}[CLSCompliant(false)]public static implicit operator Decimal(ulong value){   return new Decimal(value);}public static explicit operator Decimal(float value){   return new Decimal(value);}public static explicit operator Decimal(double value){   return new Decimal(value);}public static explicit operator byte(Decimal value){   return ToByte(value);}[CLSCompliant(false)]public static explicit operator sbyte(Decimal value){   return ToSByte(value);}public static explicit operator char(Decimal value){   UInt16 temp;   try   {      temp = ToUInt16(value);   }   catch (OverflowException e)   {      throw new OverflowException(Environment.GetResourceString("Overflow_Char"), e);   }   return (char)temp;}public static explicit operator short(Decimal value){   return ToInt16(value);}[CLSCompliant(false)]public static explicit operator ushort(Decimal value){   return ToUInt16(value);}public static explicit operator int(Decimal value){   return ToInt32(value);}[CLSCompliant(false)]public static explicit operator uint(Decimal value){   return ToUInt32(value);}public static explicit operator long(Decimal value){   return ToInt64(value);}[CLSCompliant(false)]public static explicit operator ulong(Decimal value){   return ToUInt64(value);}public static explicit operator float(Decimal value){   return ToSingle(value);}public static explicit operator double(Decimal value){   return ToDouble(value);}public static Decimal operator +(Decimal d){   return d;}public static Decimal operator -(Decimal d){   return Negate(d);}public static Decimal operator ++(Decimal d){   return Add(d, One);}public static Decimal operator --(Decimal d){   return Subtract(d, One);}[System.Security.SecuritySafeCritical]  // auto-generatedpublic static Decimal operator +(Decimal d1, Decimal d2){   FCallAddSub(ref d1, ref d2, DECIMAL_ADD);   return d1;}[System.Security.SecuritySafeCritical]  // auto-generatedpublic static Decimal operator -(Decimal d1, Decimal d2){   FCallAddSub(ref d1, ref d2, DECIMAL_NEG);   return d1;}[System.Security.SecuritySafeCritical]  // auto-generatedpublic static Decimal operator *(Decimal d1, Decimal d2){   FCallMultiply(ref d1, ref d2);   return d1;}[System.Security.SecuritySafeCritical]  // auto-generatedpublic static Decimal operator /(Decimal d1, Decimal d2){   FCallDivide(ref d1, ref d2);   return d1;}public static Decimal operator %(Decimal d1, Decimal d2){   return Remainder(d1, d2);}[System.Security.SecuritySafeCritical]  // auto-generatedpublic static bool operator ==(Decimal d1, Decimal d2){   return FCallCompare(ref d1, ref d2) == 0;}[System.Security.SecuritySafeCritical]  // auto-generatedpublic static bool operator !=(Decimal d1, Decimal d2){   return FCallCompare(ref d1, ref d2) != 0;}[System.Security.SecuritySafeCritical]  // auto-generatedpublic static bool operator <(Decimal d1, Decimal d2){   return FCallCompare(ref d1, ref d2) < 0;}[System.Security.SecuritySafeCritical]  // auto-generatedpublic static bool operator <=(Decimal d1, Decimal d2){   return FCallCompare(ref d1, ref d2) <= 0;}[System.Security.SecuritySafeCritical]  // auto-generatedpublic static bool operator >(Decimal d1, Decimal d2){   return FCallCompare(ref d1, ref d2) > 0;}[System.Security.SecuritySafeCritical]  // auto-generatedpublic static bool operator >=(Decimal d1, Decimal d2){   return FCallCompare(ref d1, ref d2) >= 0;}

慕少森

作为部分快捷方式,您可以限制double覆盖所有常规“数字”类型,但需要编译器插入强制转换。double对于较大的整数值,总是比较是危险的(int并且较小的类型始终是精确的)。class MyType {    public override bool Equals(object obj)    {        return base.Equals(obj);    }    public override int GetHashCode()    {        return base.GetHashCode();    }    public static bool operator == (MyType x, double c)    {       // write some real code here - this one does not have a value to compare to.        return c > 42;     }    // you need all several overrides for each operator to behave in expected way    // so calling the same one (a == b)    // from a != b, b != a, b == a is a way to keep them consistent    public static bool operator == (double c, MyType x)    {        return (x == c);    }    public static bool operator != (double c, MyType x)    {        return !(c == x);       }    public static bool operator != (MyType x, double c)    {        return !(x == c);    }}笔记C#/.NET 没有内置的“数字”类型概念 - 这是人们经常问的问题(即,是否存在将我的泛型方法限制为数字类型的约束?,泛型 - 其中 T 是数字?)。不要忘记实施IEquatable<T>, IComparable, IComparable<T>...考虑一下它是否真的对你的“数字”有用,能够自由地与其他类型混合 - 特别是与不精确float/double已经足够痛苦的比较。
打开App,查看更多内容
随时随地看视频慕课网APP