Substituez GetHashCode au moment de substituer Equals
Mise à jour : novembre 2007
TypeName |
OverrideGetHashCodeOnOverridingEquals |
CheckId |
CA2218 |
Catégorie |
Microsoft.Usage |
Modification avec rupture |
Modification sans rupture |
Cause
Un type public substitue Object.Equals mais ne substitue pas Object.GetHashCode.
Description de la règle
GetHashCode retourne une valeur fondée sur l'instance actuelle adaptée aux algorithmes de hachage et aux structures de données telles qu'une table de hachage. Deux objets de même type et égaux doivent retourner le même code de hachage pour garantir le bon fonctionnement des types suivants :
HashTable
Dictionary
SortDictionary
SortList
HybredDictionary
Types qui implémentent IEqualityComparer
Comment corriger les violations
Pour résoudre une violation de cette règle, fournissez une implémentation d' GetHashCode. Pour une paire d'objets de même type, vous devez garantir que l'implémentation retourne la même valeur si votre implémentation de Equals retourne true pour la paire.
Quand supprimer les avertissements
Ne supprimez aucun avertissement de cette règle.
Exemple de classe
Description
L'exemple suivant indique une classe (type référence) qui enfreint cette règle.
Code
using System;
namespace Samples
{
// Violates this rule
public class 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 bool Equals(object obj)
{
if (obj == null)
return false;
if (GetType() != obj.GetType())
return false;
Point point = (Point)obj;
if (_X != point.X)
return false;
return _Y == point.Y;
}
}
}
Commentaires
L'exemple suivant résout la violation en substituant GetHashCode.
Code
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);
}
}
}
Exemple de structure
Description
L'exemple suivant indique une structure (type valeur) qui enfreint cette règle.
Code
using System;
namespace Samples
{
// Violates this rule
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 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);
}
}
}
Commentaires
L'exemple suivant résout la violation en substituant GetHashCode.
Code
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);
}
}
}
Règles connexes
Ne pas surcharger l'opérateur égal (equals) sur les types référence
Les surcharges d'opérateur offrent d'autres méthodes nommées
Les opérateurs doivent contenir des surcharges symétriques
Subsituez Equals au moment de surcharger l'opérateur égal (equals)
Surcharger l'opérateur égal (equals) en remplaçant ValueType.Equals
Voir aussi
Référence
Indications concernant l'implémentation de Equals et de l'opérateur d'égalité (==)
HashTable