Что такое C ++ эквивалент C # Collection <T>и как вы его используете? - PullRequest
3 голосов
/ 06 декабря 2009

Мне нужно хранить список / коллекцию / массив динамически созданных объектов определенного базового типа в C ++ (и я новичок в C ++). В C # я бы использовал универсальную коллекцию, что я использую в C ++?

Я знаю, что могу использовать массив:

SomeBase* _anArrayOfBase = new SomeBase[max];

Но я не получаю ничего «бесплатно» с этим - другими словами, я не могу повторить это, оно не расширяется автоматически и так далее.

Так какие еще варианты есть?

Спасибо

Ответы [ 7 ]

17 голосов
/ 06 декабря 2009

Существует std :: vector , который является оберткой вокруг массива, но он может расширяться и будет работать автоматически. Однако это очень дорогая операция, поэтому, если вы собираетесь выполнять много операций вставки или удаления, не используйте вектор. (Вы можете использовать функцию резервирования, чтобы зарезервировать определенное количество места)

std :: list - это связанный список, который имеет гораздо более быстрое время вставки и удаления, но итерация медленнее, поскольку значения не сохраняются в смежной памяти, что означает, что вычисление адреса намного сложнее и вы не сможете использовать кеш процессоров при переборе списка.
Основным преимуществом по сравнению с вектором или deque является то, что элементы могут быть добавлены или удалены из любого места в списке довольно дешево.

В качестве компромисса есть std :: deque , который внешне работает аналогично вектору, но внутренне они очень разные. Хранилище в деке не обязательно должно быть смежным, поэтому его можно разделить на блоки, что означает, что при росте декы не нужно перераспределять пространство для хранения всего содержимого. Доступ немного медленнее, и вы не можете сделать арифметику указателя, чтобы получить элемент.

9 голосов
/ 06 декабря 2009

Вы должны использовать вектор.

#include <vector>

int main()
{
  std::vector<SomeBase*> baseVector;
  baseVector.push_back(new SomeBase());
}

C ++ содержит коллекцию контейнеров данных в STL. Проверьте это здесь .

4 голосов
/ 06 декабря 2009

Вы должны использовать один из контейнеров

std::vector<SomeBase>
std::list<SomeBase>

и если вам действительно нужны динамически размещаемые объекты

std::vector<boost::shared_ptr<SomeBase>>
std::list<boost::shared_ptr<SomeBase>>
2 голосов
/ 06 декабря 2009

Все упоминали, что общий SC ++ L контролирует, но при C ++ это делается еще одна важная оговорка (которую Чаоз включил в его пример ).

В C ++ ваша коллекция должна быть настроена на SomeBase*, , а не на SomeBase. Если вы попытаетесь присвоить экземпляр производного типа экземпляру базового типа, вы в итоге вызовете то, что называется срезы объектов . Это почти совсем не то, что вы пытаетесь сделать.

Поскольку вы пришли из C #, просто помните, что "SomeBase MyInstance" означает что-то очень различное в обоих языках. С ++, эквивалентный этому, обычно "SomeBase* MyPointer" или "SomeBase& MyReference".

1 голос
/ 06 декабря 2009

Я большой поклонник std :: deque. Если вы хотите что-то бесплатно, декарь вам их даст. Быстрый доступ из головы и хвоста списка. итераторы, reverse_iterators, быстрая вставка в голову и хвост. Это не супер специализировано, но вы хотели бесплатные вещи. ; -)

Кроме того, я свяжу отличную ссылку на STL. STL - это место, где вы получаете все стандартные «бесплатные» материалы на C ++. Стандартная библиотека шаблонов . Наслаждайтесь!

1 голос
/ 06 декабря 2009

Используйте vector. Посмотрите здесь .

0 голосов
/ 06 декабря 2009

Используйте STL. Например, std :: vector и std :: set. Существует множество примеров.

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