Глава 18. Классы-контейнеры_________________________________467
последовательных контейнерах хранятся один за другим, а в ассоциативных контейнерах — в порядке, определяемом значением пользовательского ключа подобно тому, как это реализовано в контейнере-словаре из библиотеки BIDS.
Существуют три последовательных контейнера:
• Вектор (vector)
• Двусторонняя очередь (deque)
• Список (list)
Векторы подобны массивам языка С. Элементы доступны в произвольном порядке, обычно с помощью индексной операции []. Векторы STL, однако, имеют некоторые преимущества перед массивами С. Векторы хранят текущую информацию о себе: размер и число элементов в контейнере. Размер вектора может быть изменен в случае необходимости. Вектор STUDENT создается следующим образом:
typedef vector<STUDENT> STUDENT_VECTOR;
STUDENTJVECTOR student Vector;
Двусторонняя очередь подобна вектору за исключением того, что позволяет добавлять элементы как в начало, так и в конец контейнера. Чтобы не запутаться, можно добавлять элементы только в начало, однако для этого может понадобиться перемещение всех элементов. Вектор увеличивается в размере только в одном направлении, тогда как двусторонняя очередь — в обоих, что делает ее удобной для реализации структур типа FIFO. В следующем примере создается двусторонняя очередь и в нее копируется 5 одинаковых объектов STUDENT:
typedef deque<STUDENT> STUDENTJ3EQUE;
STUDENTJ3EQUE studentDeque(5, STUDENT("StudentX",0.0));
Контейнер список — это двунаправленный список, каждый узел которого содержит указатель на следующий и на предыдущий узел, что позволяет проходить его в обоих направлениях. Списки достаточно эффективны при добавлении элементов в середину контейнера или удалении их оттуда, но гораздо менее эффективны при реализации произвольного доступа. Списки не имеют операции [ ], для того чтобы добраться до нужного элемента, их нужно последовательно просматривать. Следующий фрагмент кода создает список объектов STUDENT и копирует все элементы из двусторонней очереди studentDeque начиная с головы, за исключением первого:
typedef list<STUDENT> STUDENT_LIST;
STUDENT_LIST studentList(++studentDeque.begin(), studentDeque.end()) ;
Как уже описывалось в предыдущем разделе, контейнеры-адаптеры несут в себе существующий контейнер и используют этот внутренний контейнер для обеспечения нужной функциональности адаптера. Существуют три типа контейнеров-адаптеров: