4

マップ コンテナーに remove_if テンプレートを使用しようとしましたが、テンプレート引数のコンパイラ エラーが発生しました。理由がわかりません。

int main()
{
  map<const int, int> intmap;

  intmap[1] = 1;
  intmap[2] = 2;
  intmap[3] = 3;
  intmap[4] = 4;

  auto isOdd = [&](pair<const int, int> it)->bool 
     { return static_cast<bool>(it.second % 2); };

  isOdd(*(intmap.begin()));

 remove_if(intmap.begin(), intmap.end(), isOdd); 
}

この remove_if はコンパイラ エラーをスローしています。それを修正するための提案はありますか?

エラーメッセージは

C:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\INCLUDE\utility(260) : error C2166: l-value specifies const object
        C:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\INCLUDE\utility(259) : while compiling class template member function 
        'std::pair<_Ty1,_Ty2> &std::pair<_Ty1,_Ty2>::operator =(std::pair<_Ty1,_Ty2> &&)'
        with
        [
            _Ty1=const int,
            _Ty2=int
        ]
        maperaseif.cpp(29) : see reference to class template instantiation 'std::pair<_Ty1,_Ty2>' being compiled
        with
        [
            _Ty1=const int,
            _Ty2=int
        ]
4

3 に答える 3

2

この小さなerase_ifテンプレート化された関数は、あなたが望むことをするはずです。(私はそれを書いたのではなく、どこかから拾っただけです - 書いた人に感謝します!)

  template< typename ContainerT, typename PredicateT >
  void erase_if( ContainerT& items, const PredicateT& predicate ) {
    for( auto it = items.begin(); it != items.end(); ) {
      if( predicate(*it) ) it = items.erase(it);
      else ++it;
    }
  };

あなたの例では、次のように使用します。

erase_if(intmap, isOdd); 
于 2015-03-12T07:39:37.623 に答える
1

その値の型は実際には であるため、 remove_ifonを使用することはできませんが、 remove_if の要件を見ると、逆参照された反復子の型が であることがわかります。mapstd::pair<const Key, Value>MoveAssignable

ループを書くか、たとえばブーストを使用してください。

于 2015-03-12T07:34:14.427 に答える