覆寫實值型別上的等號和等號比較運算子
更新:2007 年 11 月
型別名稱 |
OverrideEqualsAndOperatorEqualsOnValueTypes |
CheckId |
CA1815 |
分類 |
Microsoft.Performance |
中斷變更 |
非中斷 |
原因
公用實值型別 (Value Type) 未覆寫 Object.Equals,或未實作等號比較運算子 (==)。此規則不會檢查列舉型別 (Enumeration)。
規則描述
對於實值型別而言,Equals 的繼承實作會使用 Reflection 程式庫,並比較所有欄位的內容。但是 Reflection 相當耗費運算資源,而且可能不需要比較每個欄位是否相等。如果希望使用者比較或排序執行個體,或是以它們做為雜湊資料表索引鍵,則您的實值型別應實作 Equals。如果您的程式語言支援運算子多載,那麼還需要提供等號比較運算子和不等比較運算子的實作。
如何修正違規
若要修正此規則的違規情形,請提供 Equals 的實作。如果可以的話,請實作等號比較運算子。
隱藏警告的時機
如果實值型別的執行個體不會互相比較,則您可以放心地隱藏這項規則的警告。
違規範例
說明
下列範例顯示違反此規則的結構 (實值型別)。
程式碼
using System;
namespace Samples
{
// Violates this rule
public struct Point
{
private readonly int _X;
private readonly int _Y;
public Point(int x, int y)
{
_X = x;
_Y = y;
}
public int X
{
get { return _X; }
}
public int Y
{
get { return _Y; }
}
}
}
修正方式範例
說明
下列範例將透過覆寫 ValueTypeEquals() 及實作等號比較運算子 (==、!=) 的方式,修正前述的違規情形。
程式碼
using System;
namespace Samples
{
public struct Point : IEquatable<Point>
{
private readonly int _X;
private readonly int _Y;
public Point(int x, int y)
{
_X = x;
_Y = y;
}
public int X
{
get { return _X; }
}
public int Y
{
get { return _Y; }
}
public override int GetHashCode()
{
return _X ^ _Y;
}
public override bool Equals(object obj)
{
if (!(obj is Point))
return false;
return Equals((Point)obj);
}
public bool Equals(Point other)
{
if (_X != other._X)
return false;
return _Y == other._Y;
}
public static bool operator ==(Point point1, Point point2)
{
return point1.Equals(point2);
}
public static bool operator !=(Point point1, Point point2)
{
return !point1.Equals(point2);
}
}
}
相關規則
覆寫 ValueType.Equals 時必須一併多載等號比較運算子