Практическое использование шаблона & ldquo; Curiously Recurring Template Pattern & rdquo;

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

41
задан HostileFork 2 September 2015 в 13:40
поделиться

6 ответов

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

20
ответ дан moonshadow 2 September 2015 в 13:40
поделиться

CRTP становится намного менее любопытным, если Вы полагаете, что тип подкласса, который передается суперклассу, только необходим во время расширения метода. Таким образом все типы определяются. Вам просто нужен шаблон для импорта символьного типа подкласса в суперкласс, но это - просто предописание - как все формальные шаблонные типы параметрического усилителя по определению - насколько суперкласс затронут.

Мы используем в несколько измененной форме, передавая подкласс в, черты вводят структуру к суперклассу для позволения суперклассу к эхо-сигналам производного типа. Приложение является библиотекой для геометрического исчисления (точки, векторы, строки, поля), где вся универсальная функциональность реализована в суперклассе, и подкласс просто определяет определенный тип: CFltPoint наследовался TGenPoint. Также CFltPoint существовал перед TGenPoint, таким образом разделяя на подклассы был естественный способ осуществить рефакторинг это.

4
ответ дан QBziZ 2 September 2015 в 13:40
поделиться

Для реального использования библиотеки CRTP посмотрите на ATL и WTL (wtl.sf.net). Это используется экстенсивно там для полиморфизма времени компиляции.

1
ответ дан Roel 2 September 2015 в 13:40
поделиться

Это также особенно полезно для mixins (которым я имею в виду классы, которым Вы наследовались обеспечить функциональность), который сами должен знать то, что вводит, они воздействуют на (и следовательно должны быть шаблоны).

В Эффективный C++ , Scott Meyers обеспечивает как пример шаблон класса NewHandlerSupport< T>. это содержит статический метод переопределить новый обработчик для конкретного класса (таким же образом, что станд.:: set_new_handler делает для нового оператора по умолчанию), и оператор, новый, который использует обработчик. Для обеспечения обработчика на тип родительский класс должен знать то, что вводит его, действует на, таким образом, это должен быть шаблон класса. Шаблонный параметр является дочерним классом.

Вы не могли действительно сделать этого без CRTP, так как Вам нужен шаблон NewHandlerSupport, который инстанцируют отдельно, с отдельным статическим элементом данных для хранения текущего new_handler, в классе, который использует его.

, Очевидно, целый пример чрезвычайно неориентирован на многопотоковое исполнение, но он иллюстрирует тезис.

Meyers предполагает, что CRTP мог бы думаться, поскольку "Делают Это Для Меня". Я сказал бы, что это обычно имеет место для любого смешивания, и CRTP применяется в случае, где Вам нужен смесительный шаблон, а не просто смесительный класс.

20
ответ дан Steve Jessop 2 September 2015 в 13:40
поделиться

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

1
ответ дан Greg Rogers 2 September 2015 в 13:40
поделиться

Это чувствует вид подобного макроса C: воспользуйтесь преимуществом, что макрос компилируется не во время определения, а во время использования.

#define CALL_THE_RIGHT_FOO foo()

файл A:

static void foo() {
   // do file A thing
}
...
CALL_THE_RIGHT_FOO
...

файл A:

static void foo() {
   // do file B thing
}
...
CALL_THE_RIGHT_FOO
...

шаблонный шаблон использования, который Вы описываете, позволяет нам, действительно "называют правильное нечто" в родительском шаблоне, откладывая определение того, что точно правильное нечто, пока шаблон не инстанцируют. Кроме этого случая вот в чем разница между ClassA:: нечто и ClassB:: нечто на основе значения T в Родителе.

-1
ответ дан Arkadiy 2 September 2015 в 13:40
поделиться
Другие вопросы по тегам:

Похожие вопросы: