2014-12-26 3 views
10

Я пытаюсь реализовать семантику ключевого слова D-языка inout на C++ (просто для удовольствия).Автоматическая генерация перегрузки const для функции-члена

В зависимости от контекста, она по существу говорит одна из двух вещей:

  1. «Результат этой функции будет иметь ту же константную-ность в качестве одного из своих аргументов.»
  2. «Результат этой функции-члена будет иметь ту же самую константу, что и экземпляр, на который вы его называете».

Полезно при написании функций-членов, таких как begin и , среди других случаев.

Я был в состоянии создать обоснованную реализацию первого случая с относительной легкостью (хотя интерфейс уверен, не очень): http://ideone.com/wgaDJJ

Во-вторых, однако, по-видимому, невозможно моим лучшим предположением. Насколько я знаю, вы можете получить такую ​​«автоматическую генерацию перегрузки констант» при использовании шаблонов, но вы не можете создавать шаблоны над этим «аргументом». В частности, вы заметите, что этот код делает не работы/компиляции: http://ideone.com/W4fTa4

Было интересно:

  1. ли я что-то пропустил? Возможно ли реализовать второй случай, не прибегая к макросам или дублированию кода?
  2. Кто-нибудь знает, есть ли предложение по стандарту WG21 по этому вопросу? (не обязательно inout, просто что-нибудь по теме)
  3. Что такое отраслевой стандарт для решения этой проблемы? (Вот, возможно, не так страшно вариант я играл с: http://ideone.com/PW0vK4)
+1

IMO - это промышленный стандарт для тиражирования функции, вызовите const из неконстантных и просто const_cast проблем. И это просто сломано и никоим образом не приемлемо. Необходим языковой механизм. –

+0

Для метода вам нужно явно добавить 'const' для' this', тогда как для аргумента константа может быть выведена в шаблоне. – Jarod42

ответ

1

Короткие ответы

  1. Нет и нет.
  2. Едва ли было связано: больше вариантов перегрузки метода придет с Concepts Light.
  3. Внесите два перегрузки метода, один const и один не - const (в основном, ваш последний пример).

Подробнее

То, что вы хотите достичь в пункте 2

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

является разновидностью более общим:

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

Единственный способ сделать это на C++ - это иметь две перегрузки метода, которые отличаются только своей константой. Поскольку тип this должен быть статически известен, вы не можете написать один метод, который работает с двумя разными типами для this. Даже с помощью методов шаблонов вы должны явно написать (или пропустить) модификатор const, так как нет возможности автоматически генерировать различные экземпляры шаблонов, основанные только на константе this. Вы должны «экстернализировать»this в некотором роде, если вы хотите иметь возможность писать единый метод шаблонов. По существу, что вы сделали в своем последнем примере.

Что касается отраслевого стандарта, вам нужно только посмотреть на стандартную библиотеку. Все контейнеры, например, имеют перегрузки методов для методов begin()/end(), которые отличаются только константой, в частности, для реализации требуемой функции. (например: http://en.cppreference.com/w/cpp/container/vector/begin)

Насколько я знаю, нет специального предложения по реализации аналогичной функции в следующем стандарте. Когда дело доходит до перегрузки, одним большим новым дополнением, которое может быть связано с C++ 17, является Concepts Light, который добавляет новые способы перегрузки методов, основанных на концепциях. См. Некоторые из презентаций/видео Эндрю Саттона по этой теме (например: https://www.youtube.com/watch?v=NZeTAnW5LL0, около 50-минутной отметки, хотя вам может понадобиться посмотреть всю вещь для фона:)