Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
C++ для начинающих (Стенли Липпман) 3-е хххх.pdf
Скачиваний:
86
Добавлен:
30.05.2015
Размер:
5.92 Mб
Скачать

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

782

// правильно: рассматриваются аргументы по умолчанию из обоих объявлений template <class Type=string, int size>

class Buffer;

(Отметим, что аргументы по умолчанию для параметров шаблонов не поддерживаются в компиляторах, реализованных до принятия стандарта C++. Чтобы примеры из этой книги, в частности из главы 12, компилировались большинством современных компиляторов, мы не использовали такие аргументы.)

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

template <class Type> class QueueItem { public:

QueueItem( const Type & ); private:

Type item; QueueItem *next;

определения шаблона QueueItem:

};

Обратите внимание, что каждое появление имени QueueItem в определении шаблона

это сокращенная запись для

QueueItem<Type>

Такую сокращенную нотацию можно употреблять только внутри определения QueueItem (и, как мы покажем в следующих разделах, в определениях его членов, которые находятся вне определения шаблона класса). Если QueueItem применяется как спецификатор типа в определении какого-либо другого шаблона, то необходимо задавать полный список параметров. В следующем примере шаблон класса используется в определении шаблона функции display. Здесь за именем шаблона класса QueueItem должны идти параметры,

template <class Type>

void display( QueueItem<Type> &qi )

{

QueueItem<Type> *pqi = &qi; // ...

т.е. QueueItem<Type>.

}

16.1.1. Определения шаблонов классов Queue и QueueItem

Ниже представлено определение шаблона класса Queue. Оно помещено в заголовочный файл Queue.h вместе с определением шаблона QueueItem:

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

783

#ifndef QUEUE_H #define QUEUE_H

// объявление QueueItem

template <class T> class QueueItem;

template <class Type> class Queue { public:

Queue() : front( 0 ), back ( 0 ) { } ~Queue();

Type& remove();

void add( const Type & ); bool is_empty() const { return front == 0;

}

private:

QueueItem<Type> *front; QueueItem<Type> *back;

};

#endif

При использовании имени Queue внутри определения шаблона класса Queue список параметров <Type> можно опускать. Однако пропуск списка параметров шаблона QueueItem в определении шаблона Queue недопустим. Так, объявление члена front

template <class Type> class Queue { public:

//...

private:

//ошибка: список параметров для QueueItem неизвестен

QueueItem<Type> *front;

является ошибкой:

}

Упражнение 16.1

(a) template <class Type> class Container1;

template <class Type, int size>

Найдите ошибочные объявления (или пары объявлений) шаблонов классов:

(b) template <class T, U, class V> class Container1;

class Container2;

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

784

(c)template <class C1, typename C2>

(d)template <typename myT, class myT>

(e)template <class Type, int *pi> class Container3 {};

class Container4 {};

(f) template <class Type, int val = 0> class Container6;

template <class T = complex<double>, int v>

class Container5;

class Container6;

Упражнение 16.2

template <class elemenType> class ListItem;

template <class elemType> class List {

public:

List<elemType>()

: _at_front( 0 ), _at_end( 0 ), _current( 0 ), _size( 0 ) {}

List<elemType>( const List<elemType> & ); List<elemType>& operator=( const List<elemType> & );

~List();

void insert( ListItem *ptr, elemType value ); int remove( elemType value );

ListItem *find( elemType value );

void display( ostream &os = cout ); int size() { return _size; }

private:

ListItem *_at_front;

ListItem *_at_end;

ListItem *_current; int _size

Следующее определение шаблона List некорректно. Как исправить ошибку?