Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What's the recommended way of iterating a container in C++11?

What's the recommended way of iterating a container in C++11?

Using

container.begin() and container.end()

Or

begin(container) and end(container)

If any, when is one preferred over the other?

like image 359
Johann Gerell Avatar asked Jan 09 '12 12:01

Johann Gerell


People also ask

What is the use of iterate over container in STL?

An iterator is used to point to the memory address of the STL container classes. For better understanding, you can relate them with a pointer, to some extent. Iterators act as a bridge that connects algorithms to STL containers and allows the modifications of the data present inside the container.

What is the use of iterator while using containers?

An iterator is an object (like a pointer) that points to an element inside the container. We can use iterators to move through the contents of the container. They can be visualised as something similar to a pointer pointing to some location and we can access content at that particular location using them.

What is container algorithm iterator?

Iterators play a critical role in connecting algorithm with containers along with the manipulation of data stored inside the containers. The most obvious form of an iterator is a pointer. A pointer can point to elements in an array and can iterate through them using the increment operator (++).

How is iterator implemented in C++?

An iterator is an object that points to an element inside a container. Like a pointer, an iterator can be used to access the element it points to and can be moved through the content of the container. Each container in the C++ Standard Library provides its own iterator, as well as some methods to retrieve it.


2 Answers

I think the new syntax with range based for loops

 for (auto item : container)

is probably the most C++11 like.

As others commented, you sometimes want auto& or  const auto& instead of auto.

like image 87
Basile Starynkevitch Avatar answered Oct 05 '22 23:10

Basile Starynkevitch


The better way is

begin(container)
end(container)

because it's more extensible. For example, template argument deduction can be used to determine the size of a static array and hence begin(my_static_array) and end(my_static_array) will work.

More generally, you can add overloads/specialisations to begin(.) end(.) and use immutable legacy types in generic algorithms.

You really only need to worry about this if you're writing a generic algorithm youself

template <typename T>
void foo (T & t)
{
    bar (begin(t), end(t)); // certainly better than bar(t.begin(), t.end())
}

In client code it doesn't matter so much. In fact, I would say don't use the new form in that case -- I like to reserve certain styles/idioms for certain circumstances, divide my mindsets. But that's just me.

for (auto i = c.begin(); i != c.end(); ++i)
   // I can see at-a-glance that c is a STL-style container.
   // That might be useful to know. I can probably dismiss static arrays
   // and unorthodox containers as possibilities.
   foo (i, c.size());
like image 32
spraff Avatar answered Oct 06 '22 01:10

spraff