0

ポインタだけでなく参照も取る名前比較用のテンプレート化されたファンクタを定義したいと考えています。これを、要素のコンテナーの通常の find_if とポインターのコンテナーに使用したいと思います (残念ながら、ptr_vector などはオプションではありません)。

これまでに見つけた最良の解決策は次のとおりです。

template <typename U>
class by_name{
  public:
    by_name(U const& pName):mName(pName) {}

    template <class T>
    typename boost::disable_if_c<boost::is_pointer<T>::value, bool>::type
    operator()(T const& pX){ return pX.getName()== mName;}

    template <class T>
    typename boost::enable_if_c<boost::is_pointer<T>::value, bool>::type
    operator()(T pX){ return pX->getName()== mName;}

private:
    U mName;
};

これは、enable_if を知らない人にとっては非常に見苦しく、理解するのが非常に難しいように見えます。ポインタと参照を同様に取るようなファンクタを書く簡単な方法はありますか?

4

2 に答える 2

3

それは次のように単純にすることができます:

template <class T>
bool operator()(T const& rX) const { return rX.getName() == mName; }

template <class T>
bool operator()(T* const pX) const { return pX->getName() == mName; }
于 2012-05-11T12:18:05.487 に答える
1

getName メンバー関数を実装するクラスは std::string 以外のものを返しますか? そうでない場合は、1 つのテンプレート パラメーターを取り除くことができます。

これは、ファンクターを実装する方法です。

class by_name
{
  public:
    by_name(const std::string& name) :
      Name(name) {}

    template <class T>
    bool operator()(T const& pX) const
    {
      return pX.getName() == Name;
    }

    template <class T>
    bool operator()(T* pX) const
    {
      if (!pX)  // how do you handle a null ptr?
        return false;
      (*this)(*pX); // @Luc Danton 
    }

  private:
    std::string Name;
};

ポインターバージョンが次のように実装されている場合

bool operator(T const* pX) const {}

何らかの理由でgccがインスタンス化を選択

bool operator(T const& pX) const with [T = A*]

ファンクタは、gcc 4.6.1 でコンパイルおよびテストされています。

于 2012-05-12T23:00:09.367 に答える