Читаем Язык программирования C++. Пятое издание полностью

Для обозначения параметра типа шаблона интуитивно понятней использовать ключевое слово typename, а не class; в конце концов, для фактического типа параметра вполне может быть использован встроенный тип, а не только класс. Кроме того, ключевое слово typename более точно указывает на то, что следующее за ним имя принадлежит типу. Однако ключевое слово typename было добавлено в язык С++ как часть стандарта С++, поэтому в устаревших программах, вероятнее всего, осталось исключительно ключевое слово class.

Параметры значения шаблона

Кроме параметров типа, в определении шаблона могут быть использованы параметры значения (nontype parameter). Параметр значения представляет значение, а не тип. При определении параметров значения вместо ключевого слова class или typename используются имена типов.

При создании экземпляра шаблона такие параметры заменяются значением, предоставленным пользователем или выведенным компилятором. Чтобы компилятор смог создать экземпляр шаблона во время компиляции, эти значения должны быть константными выражениями (см. раздел 2.4.4).

В качестве примера напишем версию функции compare(), работающую со строковыми литералами. Такие литералы представляют собой массивы типа const char. Поскольку скопировать массив нельзя, определим параметры как ссылки на массив (раздел 6.2.4). Поскольку необходима возможность сравнивать литералы разных длин, снабдим шаблон двумя параметрами значения. Первый параметр шаблона представляет размер первого массива, а второй — размер второго:

template

int compare(const char (&p1)[N], const char (&p2)[M]) {

 return strcmp(p1, p2);

}

При вызове следующей версии функции compare() компилятор будет использовать размер литералов для создания экземпляра шаблона с размерами, которыми заменяют параметры N и M:

compare("hi", "mom")

Не забывайте, что компилятор завершает строковый литерал пустым символом (см. раздел 2.1.3). В результате компилятор создаст такой экземпляр:

int compare(const char (&p1)[3], const char (&p2)[4])

Параметр значения может быть целочисленным типом, указателем, ссылкой на объект (l-значением) или на тип функции. Аргумент, связанный с целочисленным параметром значения, должен быть константным выражением. У аргументов, привязанных к указателю или ссылочному параметру значения, должна быть статическая продолжительность существования (см. главу 12). Нельзя использовать обычный (нестатический) локальный или динамический объект как аргумент шаблона для параметра значения шаблона в виде ссылки или указателя. Параметр-указатель может быть также создан как nullptr или нулевое константное выражение.

Параметр значения шаблона — это константное значение в определении шаблона. Параметр значения применим там, где требуются константные выражения, например, при определении размера массива.

Аргументы шаблона, используемые для параметров значения, должны быть константными выражениями.

Шаблоны функции со спецификаторами inline и constexpr

Шаблон функции может быть объявлен как inline (встраиваемый) или constexpr, как и обычная функция. Спецификаторы inline и constexpr располагаются после списка параметров шаблона, но перед типом возвращаемого значения.

// ok: спецификатор inline следует за списком параметров шаблона

template inline Т min(const Т&, const Т&);

// ошибка: неправильное размещение спецификатора inline

inline template T min(const T&, const T&);

Создание кода, независимого от типа

Продемонстрируем два наиболее важных принципа создания обобщенного кода на примере функции compare().

• Параметры функций в шаблоне должны быть ссылками на константу.

• При проверке в теле шаблона следует использовать только оператор сравнения <.

Объявление параметров функций ссылками на константы гарантирует возможность применения функции к типам, которые не допускают копирования. Большинство типов, включая встроенные типы, но исключая указатели unique_ptr и типы ввода-вывода, а также все использованные ранее библиотечные типы допускают копирование. Но вполне могут встретиться и другие типы, которые не допускают копирования. Сделав параметры ссылками на константы, можно гарантировать применимость таких типов в функции compare(). Кроме того, если функция compare() будет применена для больших объектов, такая конструкция позволит избежать копирования и сэкономит время при выполнении.

Некоторые читатели могут подумать, что для сравнения было бы целесообразней использовать оба оператора < и >.

// ожидаемое сравнение

if (v1 < v2) return -1;

if (v1 > v2) return 1;

Перейти на страницу:

Похожие книги

1С: Бухгалтерия 8 с нуля
1С: Бухгалтерия 8 с нуля

Книга содержит полное описание приемов и методов работы с программой 1С:Бухгалтерия 8. Рассматривается автоматизация всех основных участков бухгалтерии: учет наличных и безналичных денежных средств, основных средств и НМА, прихода и расхода товарно-материальных ценностей, зарплаты, производства. Описано, как вводить исходные данные, заполнять справочники и каталоги, работать с первичными документами, проводить их по учету, формировать разнообразные отчеты, выводить данные на печать, настраивать программу и использовать ее сервисные функции. Каждый урок содержит подробное описание рассматриваемой темы с детальным разбором и иллюстрированием всех этапов.Для широкого круга пользователей.

Алексей Анатольевич Гладкий

Программирование, программы, базы данных / Программное обеспечение / Бухучет и аудит / Финансы и бизнес / Книги по IT / Словари и Энциклопедии
1С: Управление торговлей 8.2
1С: Управление торговлей 8.2

Современные торговые предприятия предлагают своим клиентам широчайший ассортимент товаров, который исчисляется тысячами и десятками тысяч наименований. Причем многие позиции могут реализовываться на разных условиях: предоплата, отсрочка платежи, скидка, наценка, объем партии, и т.д. Клиенты зачастую делятся на категории – VIP-клиент, обычный клиент, постоянный клиент, мелкооптовый клиент, и т.д. Товарные позиции могут комплектоваться и разукомплектовываться, многие товары подлежат обязательной сертификации и гигиеническим исследованиям, некондиционные позиции необходимо списывать, на складах периодически должна проводиться инвентаризация, каждая компания должна иметь свою маркетинговую политику и т.д., вообщем – современное торговое предприятие представляет живой организм, находящийся в постоянном движении.Очевидно, что вся эта кипучая деятельность требует автоматизации. Для решения этой задачи существуют специальные программные средства, и в этой книге мы познакомим вам с самым популярным продуктом, предназначенным для автоматизации деятельности торгового предприятия – «1С Управление торговлей», которое реализовано на новейшей технологической платформе версии 1С 8.2.

Алексей Анатольевич Гладкий

Финансы / Программирование, программы, базы данных