Operator overloading ==, !=, Equals

前端 未结 4 650
醉话见心
醉话见心 2020-12-02 17:58

I\'ve already gone through question

I understand that, it is necessary to implement ==, != and Equals().

publ         


        
相关标签:
4条回答
  • 2020-12-02 18:34

    As Selman22 said, you are overriding the default object.Equals method, which accepts an object obj and not a safe compile time type.

    In order for that to happen, make your type implement IEquatable<Box>:

    public class Box : IEquatable<Box>
    {
        double height, length, breadth;
    
        public static bool operator ==(Box obj1, Box obj2)
        {
            if (ReferenceEquals(obj1, obj2))
            {
                return true;
            }
            if (ReferenceEquals(obj1, null))
            {
                return false;
            }
            if (ReferenceEquals(obj2, null))
            {
                return false;
            }
    
            return obj1.Equals(obj2);
        }
    
        public static bool operator !=(Box obj1, Box obj2)
        {
            return !(obj1 == obj2);
        }
    
        public bool Equals(Box other)
        {
            if (ReferenceEquals(other, null))
            {
                return false;
            }
            if (ReferenceEquals(this, other))
            {
                return true;
            }
    
            return height.Equals(other.height) 
                   && length.Equals(other.length) 
                   && breadth.Equals(other.breadth);
        }
    
        public override bool Equals(object obj)
        {
            return Equals(obj as Box);
        }
    
        public override int GetHashCode()
        {
            unchecked
            {
                int hashCode = height.GetHashCode();
                hashCode = (hashCode * 397) ^ length.GetHashCode();
                hashCode = (hashCode * 397) ^ breadth.GetHashCode();
                return hashCode;
            }
        }
    }
    

    Another thing to note is that you are making a floating point comparison using the equality operator and you might experience a loss of precision.

    0 讨论(0)
  • 2020-12-02 18:38

    I think you declared the Equals method like this:

    public override bool Equals(BOX obj)
    

    Since the object.Equals method takes an object, there is no method to override with this signature. You have to override it like this:

    public override bool Equals(object obj)
    

    If you want type-safe Equals, you can implement IEquatable<BOX>.

    0 讨论(0)
  • 2020-12-02 18:38

    In fact, this is a "how to" subject. So, here is the reference implementation:

        public class BOX
        {
            double height, length, breadth;
    
            public static bool operator == (BOX b1, BOX b2)
            {
                if ((object)b1 == null)
                    return (object)b2 == null;
    
                return b1.Equals(b2);
            }
    
            public static bool operator != (BOX b1, BOX b2)
            {
                return !(b1 == b2);
            }
    
            public override bool Equals(object obj)
            {
                if (obj == null || GetType() != obj.GetType())
                    return false;
    
                var b2 = (BOX)obj;
                return (length == b2.length && breadth == b2.breadth && height == b2.height);
            }
    
            public override int GetHashCode()
            {
                return height.GetHashCode() ^ length.GetHashCode() ^ breadth.GetHashCode();
            }
        }
    

    REF: https://msdn.microsoft.com/en-us/library/336aedhh(v=vs.100).aspx#Examples

    UPDATE: the cast to (object) in the operator == implementation is important, otherwise, it would re-execute the operator == overload, leading to a stackoverflow. Credits to @grek40.

    This (object) cast trick is from Microsoft String == implementaiton. SRC: https://github.com/Microsoft/referencesource/blob/master/mscorlib/system/string.cs#L643

    0 讨论(0)
  • 2020-12-02 18:41
    public class BOX
    {
        double height, length, breadth;
    
        public static bool operator == (BOX b1, BOX b2)
        {
            if (b1 is null)
                return b2 is null;
    
            return b1.Equals(b2);
        }
    
        public static bool operator != (BOX b1, BOX b2)
        {
            return !(b1 == b2);
        }
    
        public override bool Equals(object obj)
        {
            if (obj == null)
                return false;
    
            return obj is BOX b2? (length == b2.length && 
                                   breadth == b2.breadth && 
                                   height == b2.height): false;
    
        }
    
        public override int GetHashCode()
        {
            return (height,length,breadth).GetHashCode();
        }
    }
    
    0 讨论(0)
提交回复
热议问题