Переопределить CompareTo: что делать с нулевым случаем?

Что должно быть возвращено в методе CompareTo, когда данный объект null?

Библиотека MSDN показывает пример возврата 1. Но я бы предпочел выбросить ошибку, потому что сравнение с null невозможно.

Я ожидаю от этого мнения разные мнения. Каким может быть подход с лучшей практикой?

Ответ 1

Да, есть лучшая практика. Вопреки тому, что говорят другие ответы, существует ожидаемый стандарт, а не просто самое популярное поведение.

Правильный ответ приведен в документации MSDN для IComparable<T>.CompareTo и IComparable.CompareTo:

По определению любой объект сравнивается больше null и два nullссылки сравниваются друг с другом.

(Контракт, сравнение большего определяется как: if a > b then a.CompareTo(b) > 0.)

Это ожидаемое поведение также подтверждается, например, в Nullable.Compare<T>. Null всегда сравнивается как меньшее значение.

Также стоит отметить, что для не-общего сравнения несовпадающие типы не должны рассматриваться как null:

Параметр, obj, должен быть того же типа, что и класс или тип значения который реализует этот интерфейс; в противном случае исключение ArgumentException выброшены.


Это не влияет на ваш вопрос, но имейте в виду, Nullable<T> comparison operators (==, !=, <, <=, >, >=) не следует < <2 → .

Когда вы выполняете сравнения с типами NULL, если значение одного нулевых типов - null, а другой - нет, все сравнения оцените false, за исключением != (не равно). Важно не предположим, что, поскольку конкретное сравнение возвращает false, обратный случай возвращает true. В следующем примере 10 не больше, меньше или равно нулю. Только num1 != num2оценивается до true.

Существует также нечетный результат, который (int?)null == (int?)null имеет значение true, но (int?)null <= (int?)null не имеет значения.

Ответ 2

Выбор за вами. Это не выходит за рамки возможности представить действительный прецедент, где я бы ничего не сравнивал и ничего не хотел бы видеть "чем-то". Но почему вы его переопределяете, поэтому вы можете решить, как вы хотите справиться с этим делом.

Ответ 3

Лучшая практика будет зависеть от вашего конкретного случая: по сравнению с null может быть возможно в зависимости от объекта, который вы сравниваете.

Если я определяю свой объект таким образом, что null является наименьшим возможным значением для любого сравнения, то сравнение с null очевидно возможно и имеет четко определенный результат. В других случаях бросание исключения может иметь больше смысла.

В конечном счете, это (довольно субъективный) вопрос проектирования, к которому не обязательно должен отвечать один.

Ответ 4

CompareTo с нулевым аргументом влияет на случай сортировки списка с нулевыми элементами. Возвращая 1, когда данный объект имеет значение null, значение null появляется в верхней части списка при сортировке, что является самым популярным поведением.