Равенство

В Kotlin есть два типа равенства:

  • Равенство структур (== - проверка через equals())
  • Равенство ссылок (=== - две ссылки указывают на один и тот же объект)

Равенство структур

Структурное равенство проверяется оператором == и его отрицанием !=. По соглашению выражение a == b транслируется в:

a?.equals(b) ?: (b === null)

Если a не null, вызывается функция equals(Any?), иначе (т.е. если a указывает на null) b ссылочно сравнивается с null.

Заметьте, что в явном сравнении с null для оптимизации нет смысла: a == null будет автоматически транслироваться в a === null.

Чтобы обеспечить вашу реализацию проверки равенства, переопределите функцию equals(other: Any?): Boolean. Функции с тем же именем и другими сигнатурами, например equals(other: Foo), не влияют на проверку равенства с помощью операторов == и !=.

Структурное равенство не имеет ничего общего со сравнением, определяемым интерфейсом Comparable<...>, поэтому только пользовательская реализация equals(Any?) может повлиять на поведение оператора.

Равенство ссылок

Равенство ссылок проверяется с помощью оператора === и его отрицания !==. Выражение a === b является истиной тогда и только тогда, когда a и b указывают на один и тот же объект. Для значений, представленных примитивными типами во время выполнения (например, Int), проверка равенства === эквивалентна проверке ==.

Равенство чисел с плавающей точкой

Когда статически известно, что операнды проверки равенства являются Float или Double (nullable или нет), проверка выполняется в соответствии со стандартом IEEE 754 для арифметики с плавающей запятой.

В противном случае используется структурное равенство, которое противоречит стандарту, так что NaN равно самому себе, а -0.0 не равно 0.0.

См.: Равенство чисел с плавающей точкой.