Le contrat d' equals
concernant null
, est comme suit:
Pour tout non-nulle de la valeur de référence
x
,x.equals(null)
doitreturn false
.
C'est plutôt étrange, car si o1 != null
et o2 == null
, alors nous avons:
o1.equals(o2) // returns false
o2.equals(o1) // throws NullPointerException
Le fait qu' o2.equals(o1) throws NullPointerException
est une bonne chose, car il nous alerte d'erreur du développeur. Et pourtant, cette erreur ne serait pas atteint si, pour diverses raisons, nous avons tout juste de passer à d' o1.equals(o2)
, ce qui serait tout simplement "en silence l'échec" à la place.
Donc les questions sont:
- Pourquoi est-ce une bonne idée que
o1.equals(o2)
doitreturn false
au lieu de jeterNullPointerException
? - Serait-ce une mauvaise idée si dans la mesure du possible, nous réécrire le contrat de sorte qu'
anyObject.equals(null)
toujours jeterNullPointerException
à la place?
Sur la comparaison avec d' Comparable
En revanche, c'est ce que l' Comparable
contrat dit:
Notez que
null
n'est pas une instance de classe, ete.compareTo(null)
jetteNullPointerException
même sie.equals(null)
retoursfalse
.
Si NullPointerException
est approprié pour compareTo
, pourquoi n'est-il pas pour equals
?
Questions connexes
Purement semantical argument
Ce sont les mots réels en Object.equals(Object obj)
documentation:
Indique si quelque autre objet est "égal" à celui-ci.
Et qu'est ce qu'un objet?
JLS 4.3.1 Objets
Un objet est une instance de classe ou d'un tableau.
Les valeurs de référence (souvent juste références) sont des pointeurs sur ces objets, et un spécial
null
de référence, qui fait référence à aucun objet.
Mon argument à partir de cet angle est vraiment simple.
-
equals
teste si quelque autre objet est "égal"this
-
null
de référence ne donne pas d' autre objet pour le test - Par conséquent,
equals(null)
devraient jeterNullPointerException