Hi guys.
Recently i am trying to write a game state manager. And i failed to create a function that will remove all states except one.
statemanager.h
1 2 3 4 5 6 7 8 9 10 11 12 13 14
|
class StatesManager
{
public:
StatesManager();
.
.
.
void removeAllStatesExcept(StateID identifier);
private:
std::map<StateID, std::unique_ptr<State>> mStates;
};
|
StateID is an
enum class
.
And here is statemanager.cpp
1 2 3 4 5 6 7 8 9 10 11 12
|
.
.
void StatesManager::removeAllStatesExcept(StateID identifier)
{
mStates.erase(
std::remove_if(mStates.begin(), mStates.end(),
[&] (const std::pair<StateID, std::unique_ptr<State>> p)
{ return std::get<0>(p) != identifier; } )
, mStates.end());
}
.
.
|
And the compiler gives
/usr/include/c++/4.9.0/bits/predefined_ops.h:231: error: cannot bind 'std::pair<const StateID, std::unique_ptr<State> >' lvalue to 'std::pair<const StateID, std::unique_ptr<State> >&&'
{ return bool(_M_pred(*__it)); }
^
/usr/include/c++/4.9.0/bits/stl_pair.h:170: error: assignment of read-only member 'std::pair<const StateID, std::unique_ptr<State> >::first'
first = std::forward<first_type>(__p.first);
^ |
I am not well acquainted with c++11 features yet. Which confuses me about where i am doing wrong.
Thanks in advance.
Last edited on
It's not possible to use std::remove_if on associative containers like std::map.
Last edited on
That's wrong: by erasing p.first, you're invalidating the iterator that the range-for loop is going to increment next step.
Use the usual iterator-based erase loop
1 2 3 4
|
for( auto it = mStates.begin(); it != mStates.end(); ) {
if( it->first != identifier ) it = mStates.erase(it);
else ++it;
}
|
Last edited on
Thanks for the warning @Cubbi. I changed the code.
It is now
1 2 3 4 5 6
|
for(std::map<StateID, std::unique_ptr<State>>::iterator itr = mStates.begin(); itr != mStates.end(); )
{
if( itr->first != identifier )
itr = mStates.erase(itr);
else ++itr;
}
|
Didn't use
auto
just to be aware of it is an std::map iterator.
Last edited on
But i designed this as a game state manager. So most probably more than 3 states will not exist at the same time. At least for my usage purposes.
Thanks for the help though. I will consider this possibility if i ever make a container with lots of elements.
Last edited on