0

異なる関数への 2 つのポインターがあります。

typedef std::vector<double> TData;
double ( * p_test1 ) ( const TData> &arg);
double ( * p_test2 ) ( const TData> &ar1, char *arg2, char *arg3);

関数へのポインタを引数として持つメソッド

double f (double ( * p_test1 ) ( const TData  &arg ))
{
    //Long and not trivial algorithm processing results of p_test
    for ( i = 0;... )
    {
       double res = p_test (arg);  //Some computations
    }
}

f() メソッドには難しい計算が含まれています (ここでは for サイクルに置き換えられています)。

この引数 (つまり、異なる量のパラメーターを持つ関数へのポインター) をテンプレート化して、両方の型の引数を処理する一般的な関数を取得することは可能ですか?

double f (double ( * p_test1 ) ( const TData  &arg ));
double f (double ( * p_test2 ) ( const TData> &ar1, char *arg2, char *arg3));

または、関数へのポインターへのポインターを書き込むなど、そのような関数を記述する方法はありますか?

f() 関数の部分的な特殊化は複雑であるため避けたい (長いコードを繰り返し上書きするのは効率的ではない)。

ご協力いただきありがとうございます...

4

2 に答える 2

1

少なくともC++11では、確かにテンプレートを作成できます。

template <typename ...Args>
double f(double(*fp)(Args...))
{
    double res = fp( /* ??? */ );
}

問題は、関数を呼び出す方法をどのように知っているかということです。

于 2012-10-05T11:09:09.893 に答える
1

何かを取ることができるメソッドは、特殊なケースとして、関数ポインタも取ることができます。例えば

template<typename Function>
double f (Function p_test)
{ ...
    // if p_test is a function pointer or has operator(), this will work
    double res = p_test (arg);
  ... }

しかし問題は、2 つの関数が異なる引数を取っているという事実に帰着します。したがって、引数は何らかの形で にバンドルされてfいる必要があるか、とにかくいくつかの異なる実装が必要であるか、引数が常に同じである必要があります。

引数を束ねるには、通常はstd::bind(C++11) またはを使用しますboost::bind。3 つの引数 ( ) を必要とする関数があり、それを最初の引数のみを提供するtest2汎用アルゴリズム ( ) に渡す必要があるとします。fそして、あなたは他の 2 を知っています。

f(bind(&test2, _1, secondarg, thirdarg))

(C++11 ではbindisstd::bindおよび_1is std::placeholders::_1、Boost ではbindisboost::bindおよび_1is はヘッダーによって提供される匿名名前空間にあります。) この場合、 の戻り値の型は適切な を持つ未指定のクラス型fであるため、任意の引数を取る必要があります。bindoperator()

于 2012-10-05T12:50:57.040 に答える