Зачем использовать параметр, не являющийся типом, в C ++? - PullRequest
3 голосов
/ 01 августа 2020

Я читал здесь документацию по объекту массива на C ++: https://en.cppreference.com/w/cpp/container/array и увидел, что заголовок шаблона был

template<
    class T,
    std::size_t N
> struct array;

Почему N передается как параметр, не являющийся типом, а не структура, имеющая конструктор, который принимает размер в качестве переменной? ?

Ответы [ 2 ]

2 голосов
/ 01 августа 2020

По сути, в STL есть два класса массивов:

  • std::vector - это оболочка для динамически выделяемого массива. Его размер может быть изменен во время выполнения и, следовательно, может быть задан в конструкторе.

  • std::array с другой стороны, это оболочка для массива stati c (например, int values[10]; ). Его размер должен быть известен во время компиляции и не может быть изменен во время выполнения. Поэтому размер является параметром шаблона и не может быть передан в конструктор.

2 голосов
/ 01 августа 2020

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

std::array является хорошим примером для этого . Я предполагаю, что его определение класса имеет член данных, который представляет собой простой массив с размером N, например,

template<class T, std::size_t N>
struct array {
   // ...

   T wrapped[N];
};

Если N было значением времени выполнения (например, переданным конструктору), нет способ делать такие вещи.

Другой пример, когда такая «конфигурация» во время компиляции шаблонов классов полезна, - это «маленькие векторы», то есть контейнеры с фиксированным размером буфера, откладывающие динамическое c выделение памяти до точки, где этот буфер заполнен. Такой размер буфера также можно указать только с параметром шаблона, отличным от типа. А учитывая, что выделение памяти может быть узким местом производительности, такие методы имеют большое значение.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...