Перегрузка операторов доступа членов ->,.* (С++)

Я понимаю большинство перегрузок операторов, за исключением операторов доступа членов ->, .*, ->* etc.

в частности, что передается этим функциям оператора и что должно быть возвращено?

как работает оператор (например,operator->(...) ) знаете, на какой член ссылаются? Может ли он знать? Ему вообще нужно знать?

наконец, есть ли какие-либо соображения const, которые необходимо учитывать? Например, когда перегрузка что-то вроде operator[], как правило, вам понадобится как const, так и non-const версия. Требуются ли операторам доступа к членам версии const и non-const?

5 ответов


->

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

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


оператор -> специальные.

" Он имеет дополнительные нетипичные ограничения: он должен возвращать объект (или ссылку на объект), который также имеет оператор разыменования указателя, или он должен возвращать указатель, который может использоваться для выбора того, на что указывает стрелка оператора разыменования указателя." Брюс Экель: мышление CPP Vol-one: оператор ->

дополнительная функциональность предоставляется для удобства, поэтому вам не нужно звонить

a->->func();

вы можно просто сделать:

a->func();

это делает оператор - > отличным от других перегрузок оператора.


вы не можете перегрузить доступ к члену . (т. е. вторая часть чего -> делает). Однако вы можете перегрузить унарный разыменование оператор * (т. е. первая часть того, что -> делает).

C++ -> оператор в основном представляет собой объединение двух шагов, и это ясно, если вы думаете, что x->y эквивалентно (*x).y. C++ позволяет настроить, что делать с (*x) когда x экземпляр класс.

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


на -> оператор не знает, на какой элемент указывается, он просто предоставляет объект для выполнения фактического доступа к элементу.

кроме того, я не вижу причин, по которым вы не можете предоставить версии const и non-const.


когда вы перегружаете оператор - > () (здесь аргументы не передаются), компилятор фактически вызывает -> рекурсивно, пока он не вернет фактический указатель на тип. Затем он использует правильный элемент/метод.

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

Что касается constness-на него ответили в комментариях и других ответах (вы можете и должны предоставить оба).