Контракт equals в отношении null выглядит следующим образом:
Для любого ненулевого опорного значения
x,x.equals(null)долженreturn false.
Это довольно странно, потому что если o1 != null и o2 == null, то мы имеем:
o1.equals(o2) // returns false
o2.equals(o1) // throws NullPointerException
Тот факт, что o2.equals(o1) throws NullPointerException - это хорошо, потому что он предупреждает нас об ошибке программиста. И тем не менее, эта ошибка не была бы решена, если по разным причинам мы просто переключили ее на o1.equals(o2), которая просто "молчала бы" вместо этого.
Итак, вопросы:
- Почему это хорошая идея, что
o1.equals(o2)долженreturn falseвместо метанияNullPointerException? - Было бы плохой идеей, если, по возможности, мы переписываем контракт так, чтобы
anyObject.equals(null)всегда бросалNullPointerExceptionвместо этого?
По сравнению с Comparable
В отличие от этого, Comparable контракт говорит:
Обратите внимание, что
nullне является экземпляром какого-либо класса, аe.compareTo(null)должен бросатьNullPointerException, хотяe.equals(null)возвращаетfalse.
Если NullPointerException подходит для compareTo, почему это не для equals?
Связанные вопросы
Чистый семантический аргумент
Это фактические слова в Object.equals(Object obj):
Указывает, является ли какой-либо другой объект "равным" этому.
А что такое объект?
Объекты JLS 4.3.1
Объект - это экземпляр класса или массив.
Контрольные значения (часто просто ссылки) являются указателями на эти объекты и специальной ссылкой
null, которая ссылается на отсутствие объекта.
Мой аргумент из этого угла действительно прост.
-
equalsпроверяет, равен ли какой-либо другой объект "<" t228 > -
nullссылка не дает другого объекта для теста - Поэтому
equals(null)должен бросатьNullPointerException