С++ для начинающих




Вывод аргументов шаблона * - часть 4


Ограничение на допустимые типы преобразований относится только к тем фактическим параметрам функции, которые принимают участие в выводе аргументов шаблона. К остальным аргументам могут применяться любые трансформации. В следующем шаблоне функции sum() есть два формальных параметра. Фактический аргумент op1 для первого параметра участвует в выводе аргумента Type шаблона, а второй фактический аргумент op2 – нет.

template <class Type>

   Type sum( Type op1, int op2 ) { /* ... */ }

Поэтому при конкретизации шаблона функции sum() его можно подвергать любым трансформациям. (Преобразования типов, применимые к фактическим аргументам функции, описываются в разделе 9.3.) Например:

int ai[] = { ... };

double dd;

int main() {

   // конкретизируется sum( int, int )

   sum( ai[0], dd );

}

Тип второго фактического аргумента функции dd не соответствует типу формального параметра int. Но это не мешает конкретизировать шаблон функции sum(), поскольку тип второго аргумента фиксирован и не зависит от параметров шаблона. Для этого вызова конкретизируется функция sum(int,int). Аргумент dd приводится к типу int с помощью преобразования целого типа в тип с плавающей точкой.

Таким образом, общий алгоритм вывода аргументов шаблона можно сформулировать следующим образом:

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

2.      Если параметр шаблона найден, то путем анализа типа фактического аргумента выводится соответствующий аргумент шаблона.

3.      Тип фактического аргумента функции не обязан точно соответствовать типу формального параметра. Для приведения типов могут быть применены следующие преобразования:

  • трансформации l-значения
  • преобразования спецификаторов
  • приведение производного класса к базовому при условии, что формальный параметр функции имеет вид T<args>& или T<args>*, где список аргументов args содержит хотя бы один параметр шаблона.
  • 4.      Если один и тот же параметр шаблона найден в нескольких формальных параметрах функций, то аргумент шаблона, выведенный по каждому из соответствующих фактических аргументов, должен быть одним и тем же.

    Упражнение 10.4

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

    Упражнение 10.5

    Пусть даны следующие определения шаблонов:

    template <class Type>

       Type min3( const Type* array, int size ) { /* ... */ }

    template <class Type>

       Type min5( Type p1, Type p2 ) { /* ... */ }

    Какие из приведенных ниже вызовов ошибочны? Почему?

    double dobj1, dobj2;

    float fobj1, fobj2;

    char cobj1, cobj2;

    int ai[5] = { 511, 16, 8, 63, 34 };

    (a) min5( cobj2, 'c' );

    (b) min5( dobj1, fobj1 );

    (c) min3( ai, cobj1 );




    Содержание  Назад  Вперед