// ...

}

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

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

#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:

QueueItemType *front;

QueueItemType *back;

};

#endif

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

template class Type

class Queue {

public:

// ...

private:

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

QueueItemType *front;

}

Упражнение 16.1

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

(a) template class Type

class Container1;

template class Type, int size

class Container1;

(b) template class T, U, class V

class Container2;

(c) template class C1, typename C2

class Container3 {};

(d) template typename myT, class myT

class Container4 {};

(e) template class Type, int *pi

class Container5;

(f) template class Type, int val = 0

class Container6;

template class T = complexdouble, int v

class Container6;

Упражнение 16.2

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

template class elemenType

class ListItem;

template class elemType

class List {

public:

ListelemType()

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

{}

ListelemType( const ListelemType & );

ListelemType& operator=( const ListelemType & );

~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

};

<p>16.2. Конкретизация шаблона класса</p>

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

Queueint qi;

то из обобщенного определения шаблона автоматически создается класс Queue для объектов типа int.

Генерация конкретного класса из обобщенного определения шаблона называется конкретизацией шаблона. При такой конкретизации Queue для объектов типа int каждое вхождение параметра Type в определении шаблона заменяется на int, так что определение класса Queue принимает вид:

template class int

class Queue {

public:

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

~Queue();

int& remove();

void add( const int & );

bool is_empty() const {

return front == 0;

}

private:

QueueItemint *front;

QueueItemint *back;

};

Чтобы создать класс Queue для объектов типа string, надо написать:

Queuestring qs;

При этом каждое вхождение Type в определении шаблона будет заменено на string. Объекты qi и qs являются объектами автоматически созданных классов.

Каждый конкретизированный по одному и тому же шаблону экземпляр класса совершенно не зависит от всех остальных. Так, у Queue для типа int нет никаких прав доступа к неоткрытым членам того же класса для типа string.

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

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