При перегрузке оператора «==» в c ++ существует ли стандартное определение относительно того, что явно означает равенство, или набор рекомендаций относительно того, как «==» должен вести себя?
В настоящее время у меня есть класс, который не хранит всю свою сущность в памяти. Он в основном использует очередь с приоритетами, чтобы определить, как часто используется объект внутри себя, и когда объекты извлекаются из конца очереди, они удаляются из памяти и записываются на диск.
Так что теперь проблема возникает с равенством, что означает, что два из этих объектов равны. Поскольку мы можем начать с объектов A и B, которые одинаковы во всех отношениях, они загрузили одни и те же данные в память и имеют одинаковые данные на диске. Но затем, после вызова ряда функций на A и B, теперь они могут отличаться. A и B по-прежнему имеют одинаковые данные на диске, но они имеют разные данные, загруженные в память. Так что вопрос должен A == B
принять истину или ложь?
Есть ли набор правил или рекомендаций, которые определяют, как это должно работать? Или это просто ситуация, когда я решаю, что для программы наиболее целесообразно, и документирую, что делает «==»?
В стандарте нет определения того, как перегружен operator ==
должен вести себя
Но достаточно хорошая рекомендация такова: если вам нужно думать об этом так долго, как вы, вероятно, не стоит даже перегружать operator ==
, Если это не интуитивно, это приносит больше вреда, чем пользы.
Таким образом, вопрос заключается в том, должен ли A == B разрешить значение true или false?
ИМО, это должно привести к ошибке компилятора. 🙂
любой operator==
перегрузка должна уважать аксиомы отношение эквивалентности, то есть
x == x
, для всех объектов x
x == y
, затем y == x
x == y
а также y == z
, затем x == z
,Многие алгоритмы, использующие ==
полагаться на то, что он реализует отношение эквивалентности, формализованное в §17.6.3.1 в качестве EqualityComparable
концепция.
ВСЕ оператор перегрузки должен делать то, что вы ожидаете. Нет смысла иметь оператор ==, который возвращает истину, если объекты по существу не совпадают. То, как вы определяете «то же самое», — это, конечно, потенциально то, о чем мы могли бы поспорить. Можно реализовать «строку nocasestring», где она ведет себя как строка, но если у вас есть строка «HELLO» и один «hello», они считаются равными, потому что регистр не имеет значения. Или, если вы реализовали свой собственный класс «Float», где == выполняет некоторые математические операции, чтобы избежать хрупкого сравнения обычной плавающей запятой. Так что да, есть случаи, когда == не подходит ТОЧНО «для всех элементов есть a. == b.», Но это действительно должно быть исключением.
Аналогично, если оператор не имеет смысла, не заставляйте его делать что-то «удивительное» (например, -
для строк — что это делает? Или умножьте одну строку на другую — умножение на целое может иметь значение).
Сюрпризы в программировании — плохая идея. Если что-то не работает так, как вы ОЖИДАЕТЕ, вы получите плохой опыт от чтения / изменения кода.