equals和== 关系

139 阅读3分钟

目录

    1. 什么是 == 操作符?
    1. 什么是 equals() 方法?
    1. == 和 equals() 有什么区别?
    1. hashCode() 方法是什么?
    1. equals() 和 hashCode() 的关系是什么?
    1. 如何正确实现 equals() 和 hashCode()?
    1. 为什么 hashCode() 的实现是重要的?
    1. hashCode() 的计算通常怎么做?
    1. equals() 和 hashCode() 不一致会有什么后果?
    1. 总结:如何使用 equals() 和 hashCode()?

🤔 1. 什么是 == 操作符?

== 用于比较两个变量的值:

  • 🔍 基本数据类型:比较的是它们的值。

    int a = 5;
    int b = 5;
    System.out.println(a == b); // 输出: true
    
  • 🔍 引用类型:比较的是两个对象的内存地址(即它们是否引用同一个对象)。

    String str1 = new String("hello");
    String str2 = new String("hello");
    System.out.println(str1 == str2); // 输出: false
    

🤔 2. 什么是 equals() 方法?

equals() 方法是 Object 类中的一个方法,用于比较两个对象的内容是否相等。大多数类(如 String)重写了该方法:

String str1 = new String("hello");
String str2 = new String("hello");
System.out.println(str1.equals(str2)); // 输出: true

🤔 3. ==equals() 有什么区别?

  • 💡 ==:用于比较两个变量是否引用同一个对象,或者比较基本数据类型的值。
  • 💡 equals() :用于比较两个对象的内容是否相同(前提是该类重写了 equals() 方法)。

🤔 4. hashCode() 方法是什么?

hashCode() 方法是 Object 类中的一个方法,它返回一个对象的哈希码值(一个 int 类型的整数),该值用于确定对象在哈希表中的存储位置。

🤔 5. equals()hashCode() 的关系是什么?

  • 📌 基本规则:如果两个对象通过 equals() 方法判断相等,那么它们必须具有相同的哈希码。
  • 📌 重写规则:如果 equals() 比较的是对象的内容而非内存地址,那么 hashCode() 必须与之保持一致。

🤔 6. 如何正确实现 equals()hashCode()

public class Person {
    private String name;
    private int age;

    public Person(String name, int age) {
        this.name = name;
        this.age = age;
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;
        Person person = (Person) o;
        return age == person.age && Objects.equals(name, person.name);
    }

    @Override
    public int hashCode() {
        return Objects.hash(name, age);
    }
}

在上述代码中,equals() 方法比较 nameage 属性,而 hashCode() 方法计算它们的哈希码。

🤔 7. 为什么 hashCode() 的实现是重要的?

  • ⚡️ 性能优化:使用 hashCode() 快速定位对象的位置,避免每次都进行完整比较。
  • ⚡️ 缓存机制:Java 对象头的markword里面会缓存第一次计算的 hashCode() 值,避免重复计算。

🤔 8. hashCode() 的计算通常怎么做?

:Java 中常用一个简单的算法,将对象的多个属性的哈希码组合起来:

@Override
public int hashCode() {
    int result = name != null ? name.hashCode() : 0;
    result = 31 * result + age;
    return result;
}

这里 31 是一个常见的常数,它是一个奇质数,有助于更均匀地分布哈希值。

🤔 9. equals()hashCode() 不一致会有什么后果?

:如果不一致,哈希集合可能会出现错误行为:

  • ⚠️ 即使两个对象的内容相同,哈希集合也无法正确查找和删除这些对象。
  • ⚠️ 哈希冲突可能导致无法正确存储对象。

🤔 10. 总结:如何使用 equals()hashCode()

  • equals() :用于比较两个对象的内容是否相同。
  • hashCode() :用于快速定位对象在哈希表中的存储位置。

关键点

  • 🎯 重写 equals() 时必须重写 hashCode()
  • 🎯 相等对象必须有相同的哈希码,但反之不一定成立。