почему оператор возврата метода переопределения equals() должен использовать альтернативные && и ||?

Я видел код ниже онлайн. класс переопределяет методы hashCode() и equals класса Object. Мне просто интересно, почему оператор возврата метода equals() должен использовать альтернативные && и ||? Могу ли я просто использовать && до конца? есть ли какая-то особая причина, по которой он должен использовать альтернативные && и ||?

class Person {

private int id;
private String firstName;
private String lastName;

@Override
public boolean equals(Object obj) {
    if (obj == this) {
        return true;
    }
    if (obj == null || obj.getClass() != this.getClass()) {
        return false;
    }

    Person guest = (Person) obj;
    return id == guest.id
            && ((firstName == null ? guest.firstName == null : firstName.equals(guest.firstName))
            || (firstName != null && firstName.equals(guest.getFirstName())))
            && ((lastName == null ? guest.lastName == null : lastName.equals(guest.lastName))
            || (lastName != null && lastName.equals(guest.getLastName())));
}

@Override
public int hashCode() {
    final int prime = 31;
    int result = 1;
    result = prime * result
            + ((firstName == null) ? 0 : firstName.hashCode());
    result = prime * result + id;
    result = prime * result
            + ((lastName == null) ? 0 : lastName.hashCode());
    return result;
}



}

person Thor    schedule 10.04.2016    source источник
comment
Этот equals метод очень трудно понять в его нынешнем виде. Я предлагаю разбить его на несколько операторов if, чтобы сделать его более читаемым.   -  person Eran    schedule 10.04.2016
comment
Это не обязательно. Я никогда не видел, чтобы это делалось таким образом. Человек, написавший это, перевернул цели при вызове равных. Я думаю, что это излишняя осторожность и недостаток понимания. Если гость имеет значение null, метод возвращает false, прежде чем он когда-либо достигнет этого беспорядка. Так зачем беспокоиться о том, что гость может быть нулевым? Вероятно, это исправление чего-то еще плохо сделанного.   -  person duffymo    schedule 10.04.2016
comment
Насколько мне известно, этот метод имеет логически неверный код, который может давать неожиданные результаты. Но, эй, @TonyStark, ты всегда можешь спросить Джарвиса!   -  person dryairship    schedule 10.04.2016
comment
так сложно научиться программировать, новички не могут понять, что мы видим, правильно или неправильно :(   -  person Thor    schedule 10.04.2016


Ответы (2)


Обе дизъюнкции могут быть заменены первым операндом ||, поскольку второй оператор просто снова покрывает вторую альтернативу десятичного оператора (при условии, что геттер возвращает значение поля)

 id == guest.id
        && (firstName == null ? guest.firstName == null : firstName.equals(guest.firstName))
        && (lastName == null ? guest.lastName == null : lastName.equals(guest.lastName));

Но я рекомендую переписать его как

id == guest.id
        && Objects.equals(firstName, guest.firstName)
        && Objects.equals(lastName, guest.lastName);
person fabian    schedule 10.04.2016

Условие ИЛИ используется в зависимости от значения имени или фамилии, соответственно учитываемых, если они null отсутствуют. Но это условие уже проверено во второй части тройки? : Оператор, поэтому вы можете удалить часть ИЛИ. Результат будет таким же

((firstName == null ? guest.firstName == null : firstName.equals(guest.firstName)) || (firstName != null && firstName.equals(guest.getFirstName())))
person Jorge    schedule 10.04.2016