25

私は最近、C++ で「関数呼び出し」演算子をオーバーロードできることを発見しました。そのためには、2 対の括弧を書かなければならないという奇妙な方法があります。

class A { 
  int n;
public: 
  void operator ()() const; 
};

そして、次のように使用します。

A a;
a();

これはいつ役に立ちますか?

4

7 に答える 7

34

これは、関数のように機能するオブジェクトである「ファンクター」を作成するために使用できます。

class Multiplier {
public:
    Multiplier(int m): multiplier(m) {}
    int operator()(int x) { return multiplier * x; }
private:
    int multiplier;
};

Multiplier m(5);
cout << m(4) << endl;

上記の印刷物20。上にリンクされたウィキペディアの記事には、より実質的な例が示されています。

于 2010-02-28T02:59:02.760 に答える
21

テンプレートを使い始めるまでは、operator() を使用することで得られるのは構文上の利点にすぎません。しかし、テンプレートを使用すると、実際の関数とファンクター (関数として機能するクラス) を同じように扱うことができます。

class scaled_sine
{
    explicit scaled_sine( float _m ) : m(_m) {}
    float operator()(float x) const { return sin(m*x); }
    float m;
};

template<typename T>
float evaluate_at( float x, const T& fn )
{
   return fn(x);
}

evaluate_at( 1.0, cos );
evaluate_at( 1.0, scaled_sine(3.0) );
于 2010-02-28T03:09:32.537 に答える
6

テンプレートを使用して実装されたアルゴリズムは、呼び出されるものが関数であるかファンクターであるかを気にせず、構文を気にします。標準のもの (for_each() など) または独自のもの。また、ファンクターは状態を持つことができ、呼び出されたときにあらゆる種類のことを行うことができます。関数は、静的ローカル変数またはグローバル変数でのみ状態を持つことができます。

于 2010-02-28T03:06:07.893 に答える
1

関数ポインターをカプセル化するクラスを作成している場合、これにより使用法がより明確になる可能性があります。

于 2010-02-28T02:56:52.833 に答える