Why can't I use the + = operator in a list iterator?
I have an iterator from std::list<std::string>
, but when I try to promote it with +=
, I get a compilation error.
Code:
#include <list>
#include <iostream>
#include <string>
int main() {
std::list<std::string> x;
x.push_front("British");
x.push_back("character");
x.push_front("Coding is unco");
x.push_back("Society");
x.push_back("City Hole");
auto iter = x.begin();
iter += 3;
//std::advance(iter, 3);
x.erase(iter);
for (auto &e: x) {
std::cout << e << "\n";
}
}
If I compile this with clang++ -std=c++11 -o li li.cpp
I get:
li.cpp:13:10: error: no viable overloaded '+=' iter += 3; ~~~~ ^ ~ 1 error generated.
Why can't I use +=
with this iterator?
source to share
Iterator for std :: list BidirectionalIterator , which doesn't support operator+=
as RandomAccessIterator .
You can use operator++
which is supported by InputIterator (including BidirectionalIterator
) something like
++iter;
++iter;
++iter;
But this is ugly. The best way, as you commented, is using std :: advance (or std :: next (since C ++ 11)), which can be used with InputIterator (including BidirectionalIterator
) and also uses the functions it supports RandomAccessIterator
.
(emphasis mine)
Complexity
Linear.
However, if
InputIt
additionally meets the requirementsRandomAccessIterator
, the complexity is constant .
So you can just use it without considering the iterator category, std::advance
will make the best choice for you. eg.
std::advance(iter, 3);
or
iter = std::next(iter, 3);
source to share
The reason is that the operator is +=
not defined for the bidirectional iterator you are using.
For all iterators, there are at least:
- Copyable and destructible, i.e.
X b(a);
andb = a;
- Can be increased, i.e.
++a
anda++
Everything else depends on the type of iterator checking the table here :
As you can see, a random access iterator will do the trick.
source to share
A is std::list::iterator
not a Random Iterator . It is not possible to "jump forward" multiple items in a list; you must iterate over the list until you reach the item you want. You can use std::advance
which will infer the best way to advance the iterator based on the category of the iterator. In case std::list::iterator
it will increment the iterator in the loop.
source to share