Итак, у меня есть список:
list<Object> myList;
myList.push_back(Object myObject);
Я не уверен, но уверен, что это будет «0-й» элемент в массиве. Могу ли я использовать какую-либо функцию, которая вернет myObject?
Object copy = myList.find_element(0);
?
vector
вместо этого?front()
.Ответы:
Если вам часто требуется доступ к N-му элементу последовательности,
std::list
который реализован как двусвязный список, вероятно, это неправильный выбор.std::vector
илиstd::deque
, вероятно, было бы лучше.Тем не менее, вы можете получить итератор для N-го элемента, используя
std::advance
:std::list<Object> l; // add elements to list 'l'... unsigned N = /* index of the element you want to retrieve */; if (l.size() > N) { std::list<Object>::iterator it = l.begin(); std::advance(it, N); // 'it' points to the element at index 'N' }
Для контейнера, который не предоставляет произвольный доступ, например
std::list
,std::advance
вызываетoperator++
время итератораN
. В качестве альтернативы, если ваша реализация стандартной библиотеки предоставляет это, вы можете вызватьstd::next
:if (l.size() > N) { std::list<Object>::iterator it = std::next(l.begin(), N); }
std::next
эффективно обертывает вызовstd::advance
, облегчая продвижениеN
времени итератора с меньшим количеством строк кода и меньшим количеством изменяемых переменных.std::next
был добавлен в C ++ 11.источник
std::advance
илиstd::next
легко вызвать UB. Нет проверки границ.std::list
не предоставляет никакой функции для получения элемента по индексу. Вы можете попытаться получить его, написав код, что я бы не рекомендовал, потому что это было бы неэффективно, если вам часто нужно это делать.Что вам нужно:
std::vector
. Используйте это как:std::vector<Object> objects; objects.push_back(myObject); Object const & x = objects[0]; //index isn't checked Object const & y = objects.at(0); //index is checked
источник
std::list<Object> l; std::list<Object>::iterator ptr; int i; for( i = 0 , ptr = l.begin() ; i < N && ptr != l.end() ; i++ , ptr++ ); if( ptr == l.end() ) { // list too short } else { // 'ptr' points to N-th element of list }
источник
Может, не самый действенный способ. Но вы можете преобразовать список в вектор.
#include <list> #include <vector> list<Object> myList; vector<Object> myVector(myList.begin(), myList.end());
Затем обратитесь к вектору с помощью оператора [x].
auto x = MyVector[0];
Вы можете поместить это во вспомогательную функцию:
#include <memory> #include <vector> #include <list> template<class T> shared_ptr<vector<T>> ListToVector(list<T> List) { shared_ptr<vector<T>> Vector { new vector<string>(List.begin(), List.end()) } return Vector; }
Затем используйте вспомогательную функцию следующим образом:
auto MyVector = ListToVector(Object); auto x = MyVector[0];
источник