Prägnante Art und Weise zu kombinieren Bereich hashcodes?

Wenn die Methoden zur Implementierung von GetHashCode - wo es erforderlich ist, dies zu tun - dargestellt von Jon Skeet hier. Wiederholte seine code:

public override int GetHashCode()
{
    unchecked //Overflow is fine, just wrap
    {
        int hash = 17;
        //Suitable nullity checks etc, of course :)
        hash = hash * 23 + field1.GetHashCode();
        hash = hash * 23 + field2.GetHashCode();
        hash = hash * 23 + field3.GetHashCode();
        return hash;
    }
}

Rollen dieser code von hand-Fehler-anfällig und Fehler können so subtil sein/schwer zu erkennen (hast du swap + und * durch Fehler?), es kann schwer sein, sich daran zu erinnern, die Kombination Regeln für verschiedene Arten, und ich weiß nicht, wie aufwendet, die geistige Anstrengung auf das schreiben/überprüfen Sie die gleiche Sache über und über wieder für verschiedene Felder und Klassen. Es kann auch verschleiern eines der wichtigsten details (Tat, ich erinnere mich auch an die Felder?) in sich wiederholenden Lärm.

Gibt es eine prägnante Art und Weise zu kombinieren Bereich hashcodes mit dem .net-Bibliothek?. Natürlich könnte ich schreiben, dass meine eigenen, aber wenn es etwas gibt, idiomatische/built-in, ich würde es vorziehen, dass.

Als ein Beispiel, in Java (mit JDK7) habe ich erreichen können, die oben mit Hilfe von:

   @Override
   public int hashCode()  
   {  
      return Objects.hash(field1, field2, field3);  
   }  

Dies wirklich hilft bei der Beseitigung von bugs und konzentrieren sich in wichtigen details.

Motivation: ich kam in eine C# - Klasse, die eine überschrieben GetHashCode(), aber die Art, wie es kombiniert die hashcodes der einzelnen Bestandteile hatte einige schwere bugs. Eine library-Funktion für die Kombination der hashcodes wäre nützlich für die Vermeidung von solchen Fehlern.

  • Was tun Sie wollen, dass?
  • Soweit ich weiß ist die nächstgelegene Sie bekommen können, ist die Verwendung von ReSharper für die Gleichstellung der Mitglieder und die hash-code-Generierung,...
  • Alle Objekte in .NET implementieren GetHashCode() wenn Sie möchten, kombinieren Sie Sie einfach stellen, was Logik, die Sie wollen, tun Sie es mit in eine helper-Methode.
  • Ich will nicht schreiben ein-Helfer-Methode. Ich will, dass jemand anderes schreibt eine standard-helper-Methode. Speziell möchte ich jemand zu schreiben, eine korrekte helper-Methode, um möglichst die Chancen zu schreiben (oder einen maintainer, es zu verändern) eine falsche Umsetzung. Es ist sehr einfach zu falsch kombinieren-hashes in einer Weise, dass führt zu vielen Kollisionen.
  • bist du immer noch nicht erklärt, WARUM Sie wollen, überschreiben Sie hashcode und so ein Zeug.
  • es gibt viele Gründe, um überschreiben von hashcode/GetHashCode. Insbesondere, ist es empfehlenswert, wenn Sie Equals überschreiben und erforderlich, wenn Sie wollen vernünftige Verhalten, wenn Ihr Objekt einen Schlüssel in einer Hashtabelle. msdn.microsoft.com/en-us/library/system.object.gethashcode.aspx
  • Hashtable war vor 8 Jahren, und Sie brauchen einen guten Grund zu überschreiben Equals() auch
  • OK, also ist die fundamentale Voraussetzung für Ihre position, dass es nur wenige Gründe, die für die meisten Entwickler zu überschreiben GetHashCode, und darum, dass eine Bibliothek-Funktion ist nur von begrenztem nutzen? Das ist gut/nützlich genug Ratschläge zu setzen, eine vollständige Antwort auf ein "dies ist, wie ich Dinge tun, in Java, wie mache ich es in C#" Art von Frage.
  • Mein Punkt ist, dass ich nicht sehen, WARUM würden Sie überschreiben Equals() in solch einer täglichen basis, so dass eine helper-Methode oder die Bibliothek für das.
  • Schulterzucken. Ich überschreiben equals() und hashcode() im Java-code regelmäßig, denn Sie brauchen, wenn Sie möchten, verwenden Sie eine Klasse als hashmap Schlüssel, ohne sich auf Objekt-Identität. Vielleicht bessere Unterstützung für Werttypen in C# macht, die meist redundant (wieder, das würde für eine großartige Antwort auf die Frage). Ich fand einen buggy Umsetzung des GetHashCode() in einigen C# - code und ich dachte, das problem wäre vermieden worden, wenn, Sie würden eine standard-library-Funktion zum kombinieren der hashcodes.
  • Ich schrieb einen Helfer für diese: blog.slaks.net/2010/12/...
  • Meine Noda Time library überschreibt Equals/GetHashCode in über 20 Arten (oder bietet eine Gleichstellung comparer, die ist ziemlich ähnlich). Ich bin froh, dass der HashCodeHelper wenn es dazu kommt...
  • sorry, ich meinte Dictionary (Hashtable nicht) sowieso. Der Punkt immer noch gilt - es ist eine Implementierung einer hash-Tabelle (die sich auf GetHashCode -) wie auch immer, richtig?
  • es war ein Klasse dienen einem ähnlichen Zweck, um Ihre ValueComparer (und in der Tat umgesetzt, in einer ähnlichen Art und Weise), dass hatte den buggy Umsetzung 🙂

InformationsquelleAutor bacar | 2013-08-05
Schreibe einen Kommentar