Проблема, яка спостерігається тут, є окремим випадком більш загальної проблеми, яка полягає в тому, що кількість різних визначень рівності, які можуть бути корисні принаймні в деяких обставинах, перевищує кількість загальнодоступних засобів їх вираження. Ця проблема в деяких випадках погіршується прикрою думкою, що заплутаність у тому, що різні засоби тестування рівності дають різні результати, і подібної плутанини можна уникнути, якщо різні форми рівності дають однакові результати, коли це можливо.
Насправді основною причиною плутанини є помилкова думка, що від різних форм тестування рівності та нерівності слід очікувати того ж результату, незважаючи на те, що різні семантики корисні в різних умовах. Наприклад, з арифметичної точки зору корисно мати можливість мати такі, Decimal
які відрізняються лише кількістю зворотних нулів порівняти як рівні. Аналогічно для double
таких значень, як позитивний нуль і від’ємний нуль. З іншого боку, з точки зору кешування чи інтернування така семантика може бути смертельною. Припустимо, наприклад, у одного було Dictionary<Decimal, String>
таке, що myDict[someDecimal]
повинно дорівнюватиsomeDecimal.ToString()
. Такий об’єкт здавався б розумним, якби їх було багатоDecimal
значення, які хотіли перетворити на рядок і очікували, що там буде багато дублікатів. На жаль, якщо використовувати таке кешування для перетворення 12,3 м та 12,40 м, а потім 12,30 м та 12,4 м, останні значення отримають "12,3" та "12,40" замість "12,30" та "12,4".
Повертаючись до розглянутої справи, існує більш ніж один розумний спосіб порівняння зведених об’єктів для рівності. C # займає точку зору, на яку його ==
оператор повинен відображати поведінку Equals
. VB.NET вважає, що його поведінка повинна відображати поведінку деяких інших мов, оскільки кожен, хто хоче Equals
поведінку, може використовувати Equals
. У певному сенсі правильним рішенням було б мати тристоронню конструкцію "якщо", і вимагати, якщо умовний вираз поверне тризначний результат, код повинен вказати, що має відбуватися у null
випадку. Оскільки це не варіант із мовами, якими вони є, наступна найкраща альтернатива - просто дізнатися, як працюють різні мови, і визнати, що вони не однакові.
Між іншим, оператор "Є" Visual Basic, якого не вистачає на C, може бути використаний для перевірки того, чи є нульовий об'єкт насправді нульовим. Хоча можна обгрунтовано поставити під сумнів, чи if
повинен тест приймати a Boolean?
, тим, що нормальні оператори порівняння повертаються, Boolean?
а не Boolean
коли вони викликаються на нульові типи, є корисною функцією. До речі, у VB.NET, якщо намагається скористатись оператором рівності, а не Is
, отримуватиме попередження про те, що результат порівняння завжди буде Nothing
, і його слід використовувати, Is
якщо потрібно перевірити, чи щось недійсне.