2017-09-08 14 views
-1

我在嘗試從矢量中擦除字符串時看到一些大的錯誤消息。我試圖使用擦除刪除成語,但它不工作。這裏有一些片段來展示我的困境。如何從矢量中刪除具有給定名稱的玩家

team.players.erase(remove(team.players.begin(), team.players.end(), 
          player_name), team.players.end()); 

team.players在該結構中聲明:

struct team 
{ 
    string name; 
    player captain; 
    vector<player> players; 

}; 

載體team.players被動態地填充在程序運行時,並且在某個點,用戶具有通過去除一個玩家的選擇一份菜單。

if (select_option == PRINT_TEAM) print_team(team); 
    if (select_option == CHANGE_TEAM_NAME) change_team_name(team); 
    if (select_option == CHANGE_CAPTAIN) change_captain(team); 
    if (select_option == ADD_PLAYER) add_player(team); 
    if (select_option == REMOVE_PLAYER) remove_player(team); 
    if (select_option == QUIT) exit(0); 

但是我得到這些錯誤,因爲我試圖編譯我的程序(鐺++),該函數被調用之前很久。這裏是錯誤:

/Library/Developer/CommandLineTools/usr/bin/../include/c++/v1/algorithm:865:22: error:  invalid operands to binary expression ('player' and 'const  std::__1::basic_string<char>') 
     if (*__first == __value_) 
      ~~~~~~~~^~~~~~~~~ 
/Library/Developer/CommandLineTools/usr/bin/../include/c++/v1/algorithm:2125:22: note: 
     in instantiation of function template specialization 
     'std::__1::find<std::__1::__wrap_iter<player *>, std::__1::basic_string<char> >' 
     requested here 
    __first = _VSTD::find(__first, __last, __value_); 
        ^
program2.cpp:172:25: note: in instantiation of function template specialization 
     'std::__1::remove<std::__1::__wrap_iter<player *>, std::__1::basic_string<char> 
     >' requested here 
    team.players.erase(remove(team.players.begin(), team.players.end(), 
         ^
2 errors generated. 

任何想法我可以解決這個問題?

+4

請顯示[MCVE。 – user463035818

+3

如何創建一個比較'player'對象和'std :: string'的'operator =='函數?因爲這是編譯器告訴你的問題,所以你試圖比較'player'對象和'std :: string'。 –

+1

您的載體包含'player's所以你不能從它刪除一個字符串:P – user463035818

回答

3

該錯誤消息是相當隱祕的,特別是對於初學者,但似乎編譯器無法找到operator==實現來比較player類與std::string對象的實例。

也許你真正想要的是使用std::remove_if,指定一個自定義條件,在這個自定義條件下,你比較了玩家的名字和std::string存儲要刪除的名字。

您可以使用lambda表達此自定義條件,例如, :

team.players.erase( 
    std::remove_if(
     team.players.begin(), 
     team.players.end(), 

     [&player_name](const player& p) { 
      return p.name == player_name; 
     }), 
    team.players.end() 
); 
+0

這很好,工作。謝謝! –

+0

@LachyVass不客氣。 –

0

你想std::remove_if,不std::remove。你將不得不提供一個需要玩家的函數(const引用以避免複製)並返回bool。

例如(假定player有一個字符串構件name

team.players.erase( 
    remove_if(
     team.players.begin(), 
     team.players.end(), 
     [&player_name](const player & p) { return p.name == player_name }), 
    team.players.end()); 
0

的問題是,所述std::remove()函數使用bool operator==()player_name變量,它是std::string類型的比較std::vector<player>的元件。

這就是std::remove()識別的方式,它應該清除向量的哪些元素(或者更好地移動到容器的末尾)。

但是,沒有定義bool operator==(const player& p, const std::string& name),這並不奇怪,因爲您必須自己做。更好的方法,在這種情況下,恕我直言是使用std::remove_if()而不是std::remove(),因爲std::remove_if()需要一個一元函數(一個函數採用一個參數並返回布爾),它調用以確定它是否應該刪除該元素或不。

team.players.erase(remove_if(team.players.begin(), team.players.end(), 
    [&player_name](const auto& player) { return player.name == player_name; }); 

(注:我假定player類/結構有一個成員std::string類型的name)。使用==應該是比較 -

bool operator==(const player& p, const std::string& name) { 
    return p.name == name; 
} 

bool operator==(const std::string& name, const player& p) { 
    return p.name == name; 
    // Or, to be more general, you could use 
    // return operator==(p, name); 
    // here (to call the operator==() version with switched arguments) 
} 

(是的,你應該返回兩個版本,因爲 - 一般:

如果你想嘗試的operator==()方法,你必須定義 這樣的事情對稱)。

相關問題