Domanda

I'm trying to iterate through a vector of Player objects and then return the next one based off a Player pointer. I have tried various ways to get the operators within the lambda to match but cannot get it to work and have read similar such issues on stack overflow. I'm sorry for not making a SSCCE, I just don't know how at my current skill level.

Source of c_player:
Defined as:

Player* current_player;

Set with:

void Game::set_first_player_turn(){
    current_player = &game_players.back();
}

Erroneous code:

using namespace std;
vector<Player>game_players;

Player* Game::find_player(Player* c_player){
    vector<Player>::iterator iter;
    iter = find_if(game_players.begin(), game_players.end(),
                   [&](Player* p ) -> bool{ return p == c_player; }); //This line
                                        // causes the exception. Sets iterator to
                                        // position of the current player
    if (iter != game_players.end()){
        advance(iter, 1);
    }
    else{
        iter == game_players.begin();
    }
    current_player = &(*iter);  

    return current_player;
}

Compile error:

error C2664: 'bool Game::set_game_flow::<lambda_360ac8a355100cfac1adc9f8eba8d8b9>
::operator ()(Player *) const' : cannot convert parameter 1 from 'Player' 
to 'Player *'

Thanks for any help.

È stato utile?

Soluzione

Predicate in find_if has to take a const reference to a type stored in container. You store a Player type in vector

vector<Player> game_players;

Thus

[&](Player* p )

is not a correct predicate. This should be

[c_player]( const Player& p ) { return p == *c_player; } 
                                    // ^^^^^^^^^^^^^^
                                    // to compare by value
// note: to compare by value 
// bool operator==( const Player&, const Player&)
// must be defined

[c_player]( const Player& p ) { return &p == c_player; } 
                                    // ^^^^^^^^^^^^^^
                                    // to compare by address
// note: address of c_player
// has to be valid (not invalidated by vector through resizing, erasing, etc)

So you can write:

vector<Player>::iterator iter;
iter = find_if( game_players.begin(), game_players.end(),
                       [c_player]( const Player& p ) { return p == *c_player;});
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top