CodeGym /Java blogg /Slumpmässig /Java hashCode()
John Squirrels
Nivå
San Francisco

Java hashCode()

Publicerad i gruppen

Hash-principen

Först och främst, innan vi definierar Java-hashkoden, måste vi förstå vad som är hashing och vad det är till för. Hashing är en process för att tillämpa en hashfunktion på vissa data. En hashfunktion är bara en matematisk funktion. Oroa dig inte för detta! "Matematisk" betyder inte alltid "komplicerat". Här betyder det bara att vi har en del data och en viss regel som mappar data till en uppsättning tecken (kod). Det kan till exempel vara ett hexadecimalt chiffer. Vi har en del data av valfri storlek vid ingången och tillämpar en hashfunktion på den. Vid utgången får vi en data med fast storlek, säg 32 tecken. Vanligtvis konverterar den typen av funktion en stor bit data till ett litet heltalsvärde. Resultatet av detta funktionsarbete kallas en hashkod. Hash-funktioner används ofta i kryptografi, och även i vissa andra områden. Hashfunktioner kan vara olika,
  • Ett visst objekt har en viss hashkod.
  • Om två objekt är lika, är deras hashkoder desamma. Det omvända är inte sant.
  • Om hashkoderna är olika, är objekten inte lika med säkerhet.
  • Olika objekt kan ha samma hashkod. Det är dock en mycket osannolik händelse. Vid det här laget har vi en kollision, en situation där vi kan förlora data.
Den "riktiga" hashfunktionen minimerar sannolikheten för kollisioner.

Hashcode i Java

I Java är hash-funktionen vanligtvis kopplad till hashCode()-metoden . Exakt, resultatet av att applicera en hashfunktion på ett objekt är en hashkod. Varje Java-objekt har en hash-kod. I allmänhet är Hash Code ett tal som beräknas med metoden hashCode() för Objectklassen. Vanligtvis åsidosätter programmerare denna metod för sina objekt samt relaterad till hashCode() metoden equals() för mer effektiv bearbetning av specifik data. Metoden hashCode () returnerar ett int-värde (4 byte), vilket är en numerisk representation av objektet. Denna hashkod används till exempel av samlingar för effektivare lagring av data och därmed snabbare åtkomst till dem. Som standard är hashCode()funktion för ett objekt returnerar numret på minnescellen där objektet är lagrat. Därför, om inga ändringar görs i applikationskoden, bör funktionen returnera samma värde. Om koden ändras något ändras även hashkodvärdet. Vad används hashkoden till i Java? Först och främst hjälper Java-hashkoder program att köras snabbare. Om vi ​​till exempel jämför två objekt o1och o2av någon typ, tar operationen o1.equals(o2)cirka 20 gånger längre tid än o1.hashCode() == o2.hashCode().

Java är lika med()

I den överordnade klassen Object, tillsammans med metoden hashCode() finns det också equals() , funktionen som används för att kontrollera likheten mellan två objekt. Standardimplementeringen av den här funktionen kontrollerar helt enkelt länkarna för två objekt för deras likvärdighet. equals() och hashCode() har sitt kontrakt, så om du åsidosätter en av dem bör du åsidosätta den andra, för att inte bryta detta kontrakt.

Implementering av hashCode()-metoden

Exempel

Låt oss skapa en klasskaraktär med ett fält — namn . Efter det skapar vi två objekt av Character class, character1 och character2 och ger dem samma namn. Om vi ​​använder standard- hashCode() och equals() i klassen Object kommer vi definitivt att få olika, inte lika objekt. Det är så hashkod i Java fungerar. De kommer att ha olika hashkoder eftersom de finns i olika minnesceller och operationsresultatet equals() kommer att vara falskt.

import java.util.Objects;

public class Character {
    private String Name;

    public Character(String name) {
        Name = name;
    }

    public String getName() {
        return Name;
    }

    public void setName(String name) {
        Name = name;
    } 

    public static void main(String[] args) {
        Character character1 = new Character("Arnold");
        System.out.println(character1.getName());
        System.out.println(character1.hashCode());
        Character character2 = new Character("Arnold");
        System.out.println(character2.getName());
        System.out.println(character2.hashCode());
        System.out.println(character2.equals(character1));
    }
}
Resultatet av att köra programmet:

Arnold
1595428806
Arnold
1072408673
false
Två 10-siffriga nummer i konsolen är hashkoder. Vad händer om vi vill ha lika objekt om de har samma namn? Vad ska vi göra? Svaret: vi bör åsidosätta metoderna hashCode() och equals() i objektklassen för vår Character- klass. Vi skulle kunna göra det automatiskt i IDEA IDE, tryck bara på alt + insert på ditt tangentbord och välj Generate -> equals() och hashCode() . Vad är Java hashCode() - 2När det gäller vårt exempel har vi nästa kod:

import java.util.Objects;

public class Character {
    private String Name;

    public Character(String name) {
        Name = name;
    }

    public String getName() {
        return Name;
    }

    public void setName(String name) {
        Name = name;
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (!(o instanceof Character)) return false;

        Character character = (Character) o;

        return getName() != null ? getName().equals(character.getName()) : character.getName() == null;
    }

    @Override
    public int hashCode() {
        return getName() != null ? getName().hashCode() : 0;
    }

    public static void main(String[] args) {
        Character character1 = new Character("Arnold");
        System.out.println(character1.getName());
        System.out.println(character1.hashCode());
        Character character2 = new Character("Arnold");
        System.out.println(character2.getName());
        System.out.println(character2.hashCode());
        System.out.println(character2.equals(character1));
    }
}
Resultatet av att köra den här koden:

Arnold
1969563338
Arnold
1969563338
true
Så nu identifierar programmet våra objekt som lika och de har samma hashkoder.

Java-hashcode exempel:

Din egen hashCode() och equals()

Du kan också skapa dina egna realisationer för equals() och hashCode() , men var försiktig och kom ihåg att minimera hashkodkollisioner. Här är ett exempel på våra egna hashCode()- och equals()- metoder i Studentklassen :

import java.util.Date;

public class Student {
   String surname;
   String name;
   String secondName;
   Long birthday; // Long instead of long is used by Gson/Jackson json parsers and various orm databases

   public Student(String surname, String name, String secondName, Date birthday ){
       this.surname = surname;
       this.name = name;
       this.secondName = secondName;
       this.birthday = birthday == null ? 0 : birthday.getTime();
   }
//Java hashcode example
   @Override
   public int hashCode(){
       //TODO: check for nulls
       //return surname.hashCode() ^ name.hashCode() ^ secondName.hashCode() ^ (birthday.hashCode());
       return (surname + name + secondName + birthday).hashCode();
   }
   @Override
   public boolean equals(Object other_) {
       Student other = (Student)other_;
       return (surname == null || surname.equals(other.surname) )
               && (name == null || name.equals(other.name))
               && (secondName == null || secondName.equals(other.secondName))
               && (birthday == null || birthday.equals(other.birthday));
   }
}
Och huvudklassen för att visa sitt arbete:

import java.util.Date;
import java.util.HashMap;
import java.util.Hashtable;

public class Main {
   static HashMap<Student, Integer> cache = new HashMap<Student, Integer>(); // <person, targetPriority>

   public static void main(String[] args) {
       Student sarah1 = new Student("Sarah","Connor", "Jane", null);
       Student sarah2 = new Student("Sarah","Connor", "Jane", new Date(1970, 01-1, 01));
       Student sarah3 = new Student("Sarah","Connor", "Jane", new Date(1959, 02-1, 28)); // date not exists
       Student john = new Student("John","Connor", "Kyle", new Date(1985, 02-1, 28)); // date not exists
       Student johnny = new Student("John","Connor", "Kyle", new Date(1985, 02-1, 28)); // date not exists
       System.out.println(john.hashCode());
       System.out.println(johnny.hashCode());
       System.out.println(sarah1.hashCode());
       System.out.println();
       cache.put(sarah1, 1);
       cache.put(sarah2, 2);
       cache.put(sarah3, 3);
       System.out.println(new Date(sarah1.birthday));
       System.out.println();
       cache.put(john, 5);
       System.out.println(cache.get(john));
       System.out.println(cache.get(johnny));
       cache.put(johnny, 7);
       System.out.println(cache.get(john));
       System.out.println(cache.get(johnny));
   }
}

Vad används hashkod till?

Först och främst hjälper hashkoder program att köra snabbare. Om vi ​​till exempel jämför två objekt o1och o2av någon typ, tar operationen o1.equals(o2)ungefär 20 gånger längre tid än o1.hashCode() == o2.hashCode(). I Java står hashprincipen bakom några populära samlingar, såsom HashMap , HashSet och HashTable .

Slutsats

Varje Java-objekt har metoderna hashCode() och equals() som ärvts från klassen Object . För att få en bra fungerande jämställdhetsmekanism är det bättre att åsidosätta hashcode()- och equals()- metoderna för dina egna klasser. Att använda hashkoder gör att program körs snabbare.
Kommentarer
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION