Groovy - == 一定等价于 Java 的 equals() 吗?

简介: Groovy - == 一定等价于 Java 的 equals() 吗?

在Java中,==和equals()是一个混乱之源,而Groovy加剧了这种混乱。Groovy将==操作符映射到了Java中的equals()方法。假如我们想比较引用是否相等(也就是原始的==的语义),该怎么办呢?必须使用Groovy中的is()。下面通过一个例子来理解其区别。

GroovyForJavaEyes/Equals.groovy

str1 = 'hello'
str2 = str1
str3 = new String('hello')
str4 = 'Hello'
println "str1 == str2: ${str1 == str2}"
println "str1 == str3: ${str1 == str3}"
println "str1 == str4: ${str1 == str4}"
println "str1.is(str2): ${str1.is(str2)}"
println "str1.is(str3): ${str1.is(str3)}"
println "str1.is(str4): ${str1.is(str4)}"

来看一下Groovy中==操作符的行为以及使用is()方法的结果:

str1 == str2: true
str1 == str3: true
str1 == str4: false
str1.is(str2): true
str1.is(str3): false 
str1.is(str4): false

观察发现,Groovy的==映射到equals(),这个结论并不总是成立,当且仅当该类没有实现Comparable接口时,才会这样映射。如果实现了Comparable接口,则==会被映射到该类的compareTo()方法。

下面例子说明了这种行为。

GroovyForJavaEyes/WhatsEquals.groovy

class A {
  boolean equals(other) {
    println "equals called"
    false
  }
}
class B implements Comparable {
  boolean equals(other) {
    println "equals called"
    false
  }
  int compareTo(other) {
    println "compareTo called"
    0
  }
}
new A() == new A()
new B() == new B()

下面的输出显示,Comparable的优先级高:

equals called
compareTo called

通过输出可以看到,在实现了Comparable接口的类上,==操作符选择了compareTo(),而不是equals()。

注意 在比较对象时,请首先问一下自己,要比较的是引用还是值。然后再问一下,是不是使用了正确的操作符。

目录
相关文章
|
Java
Java中的equals()与==的区别与用法
【7月更文挑战第28天】
621 12
|
存储 Java 开发者
Java 中的 equals 方法:看似简单,实则深藏玄机
本文深入探讨了Java中`equals`方法的设计与实现。默认情况下,`equals`仅比较对象引用是否相同。以`String`类为例,其重写了`equals`方法,通过引用判断、类型检查、长度对比及字符逐一比对,确保内容相等的逻辑。文章还强调了`equals`方法需遵循的五大原则(自反性、对称性等),以及与`hashCode`的关系,避免集合操作中的潜在问题。最后,对比了`instanceof`和`getClass()`在类型判断中的优劣,并总结了正确重写`equals`方法的重要性,帮助开发者提升代码质量。
1063 1
|
存储 Java C++
java中“==”和equals,究竟比的是什么
java中“==”和equals,究竟比的是什么
276 3
java中“==”和equals,究竟比的是什么
|
存储 Java C++
java中“==”和equals,究竟比的是什么
java中“==”和equals,究竟比的是什么
347 4
|
存储 Java
【Java基础面试二十三】、==和equals()有什么区别?
这篇文章区分了Java中的`==`运算符和`equals()`方法:`==`用于基本数据类型时比较值是否相等,用于引用类型时比较内存地址是否相同;而`equals()`默认实现按内存地址比较,但通常被重写以根据对象内容比较是否相等。
【Java基础面试二十三】、==和equals()有什么区别?
【Java基础面试二十一】、说一说hashCode()和equals()的关系
这篇文章讨论了Java中`hashCode()`和`equals()`方法之间的关系,强调如果两个对象相等,它们必须有相同的哈希码,但有相同哈希码的对象未必相等,并解释了这一关系在HashSet集合中判断元素是否重复的应用场景。
【Java基础面试二十一】、说一说hashCode()和equals()的关系
【Java基础面试二十二】、为什么要重写hashCode()和equals()?
这篇文章解释了为什么需要重写`hashCode()`和`equals()`方法:因为Object类的`equals()`默认使用`==`比较,这在业务中通常是不够的,我们需要根据对象内容来比较相等性;同时,为了保持`hashCode()`与`equals()`的联动关系,一旦重写了`equals()`,通常也需要重写`hashCode()`。
【Java基础面试二十二】、为什么要重写hashCode()和equals()?
|
Java 开发者
Java一分钟之-Groovy与Java混合编程
【6月更文挑战第13天】本文探讨了Groovy与Java的混合编程,强调了Groovy在JVM上的动态特性及其与Java的高兼容性。文章指出,尽管二者可无缝共存,但仍存在类型不匹配、闭包与匿名内部类差异及语法糖导致的问题。为避免这些问题,建议在Groovy中显式指定类型、理解闭包与匿名类的区别,并制定统一编码规范。通过实例展示了Java调用Groovy脚本和Groovy调用Java类的方法,强调理解两种语言特性的重要性,以实现更高效、维护性更强的系统。
792 3
Java一分钟之-Groovy与Java混合编程
|
存储 Java 索引
java 中为什么重写 equals 后需要重写 hashCode
java 中为什么重写 equals 后需要重写 hashCode
477 8