Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Obtain an index into a vector using Iterators

When iterating over elements of a vector it is preferred to use iterators instead of an index (see Why use iterators instead of array indices?).

std::vector<T> vec;
std::vector<T>::iterator it;
for ( it = vec.begin(); it != vec.end(); ++it )
{
   // do work
}

However, it can be necessary to use the index in the body of the loop. Which of the following would be preferable in that case, considering performance and flexibility/extensibility?

  1. Revert to the indexed loop
    std::vector vec;
    size_t i;
    for ( i = 0; i < vec.size(); ++i )
    {
       // use i
    }
    
  2. Calculate offset
    std::vector vec;
    std::vector::iterator it;
    for ( it = vec.begin(); it != vec.end(); ++it )
    {
       size_t i = it - vec.begin(); 
       // use i
    }
    
  3. Use std::distance
    std::vector vec;
    std::vector::iterator it;
    for ( it = vec.begin(); it != vec.end(); ++it )
    {
       size_t i = std::distance( vec.begin(), it );
       // use i
    }
    
like image 673
andreas buykx Avatar asked Sep 25 '08 09:09

andreas buykx


4 Answers

If you're planning on using exclusively a vector, you may want to switch back to the indexed loop, since it conveys your intent more clearly than iterator-loop. However, if evolution of your program in the future may lead to a change of container, you should stick to the iterators and use std::distance, which is guaranteed to work with all standard iterators.

like image 192
Luc Touraille Avatar answered Oct 13 '22 15:10

Luc Touraille


Using std::distance is a bit more generic since it works for all iterators, not just random access iterators. And it should be just as fast as It - vec.begin() in case of random access iterators.

It - vec.begin() is basically pointer arithmetic.

like image 33
QBziZ Avatar answered Oct 13 '22 14:10

QBziZ


std::distance(vec.begin(), it) will give you the index it is pointing at, assuming it points into vec.

Carl

like image 26
Carl Seleborg Avatar answered Oct 13 '22 16:10

Carl Seleborg


Revert to the indexed loop.

Basically in 90% of the cases, iterators are superior, this is one of those 10%. By using a iterator you are making the code more complex and therefore harder to understand, when the entire reason for using the iterator in the first place was to simplify your code.

like image 27
Guvante Avatar answered Oct 13 '22 15:10

Guvante