2016-12-20 8 views
1

現在、マルチスレッドアプリケーション用にQtConncurrenctを学習しています。だから私は、リスト内の整数を合計する簡単なプログラムを実施することを決定したテストの目的のために、ここでのコードは次のとおりです。クラス内でQtConcurrent :: MappedReduceを使用する

#include <QCoreApplication> 
#include <QtConcurrent> 
#include <functional> 

class intObj{ 
    int m_value; 
public: 
    intObj(int val = 0):m_value(val){} 

    int val() const {return m_value;} 

}; 

static intObj mapFunction(const intObj &num){ 
    return intObj(num.val()); 
} 

static void reduceFunction(intObj &sum, const intObj &term){ 
    int x = sum.val(); 
    int y = term.val(); 
    sum = intObj(x+y); 
} 


class myTest{ 
    public: 
    int getSum(QList<intObj> numbers); 

}; 

int main(int argc, char *argv[]) 
{ 
    QCoreApplication a(argc, argv); 
    QList<intObj> n; 

    for(int i = 0; i < 1000 ; i++){ 
     n.append(intObj(i)); 
    } 

    myTest m; 
    int sum = m.getSum(n); 
    return a.exec(); 
} 


int myTest::getSum(QList<intObj> numbers){ 
    auto sum = QtConcurrent::mappedReduced(numbers,mapFunction,reduceFunction); 
    return sum.result().val(); 
} 

このプログラムは正しく動作しますが、マップや機能を軽減クラスの外にあります。 mapとreduce関数がintObjクラスにあるように、このプログラムを変更するにはどうすればよいですか?

私は本当に実用的な例を感謝します。前もって感謝します。

+0

元のコードを削除して質問を編集しないでください...追加情報を追加する場合は、元のコードの後に​​追加してください - 質問が大幅に変更された場合、 。 – Holt

+0

ええ、私は将来それを思い出します。 – Mafura

答えて

1

メソッドへのポインタをmappedReducedに渡すことはできません。あなたはMapFunctionとReduceFunction内部のオブジェクトを必要としない場合、あなたは2つの機能static作るべき

  • :あなたがオブジェクトを使用する必要がある場合
static int mappedFunction(const int num){ 
    return num; 
} 

static void reduce(int &sum, const int term){ 
    sum += term; 
} 
auto sum = QtConcurrent::mappedReduced(numbers, 
    std::bind(&myTest::mappedFunction, this, std::placeholders::_1), 
    std::bind(&myTest::reduce, this, std::placeholders::_1, std::placeholders::_2)); 

// Or lambda if Qt support them: 
auto sum = QtConcurrent::mappedReduced(numbers, 
    [this] (int num) { mappedFunction(num); }, 
    [this] (int &sum, int num) { reduce(sum, num); }); 

Function Objectsを使用して、現在のmyTestインスタンスへの参照を保存することもできます。

+0

現代のC++では、イディオムはラムダを使用することです。ラムダがあるときは 'std :: bind'は不要です。 –

+0

お返事ありがとうございます。私はあなたが提案した3つの方法をテストしました。最初は、3つの方法はコンパイルされませんでした。 intとvoilaの小さなラッパークラスを作成することにしました。プログラムは最初のケース(クラス外のmapFunctionとReduceFunction)に対して正しく実行されます。他の方法については、私はとても幸運ではありません。私は作業プログラムで自分の投稿を編集します – Mafura

+0

@Mafura元のコードで 'mappedFunction'と' reduce'の前に 'static'を追加するだけで、プログラムはコンパイルされます。おそらく他の場所で間違いを犯したでしょう。 – Holt

0

少しよりQtconcurrency on using member functions を開削再読み込み後、私は2つの主要な点

  1. コンテナとメンバ関数のクラスは、頭の痛みを避けるために、
  2. 同じであるべきであることに気づいこのパラメータを渡すと、ここで

が最終作業バージョン

ある静的メンバ関数を作ります
#include <QCoreApplication> 
#include <QtConcurrent> 
#include <functional> 

class intObj{ 
    int m_value; 
public: 
    intObj(int val = 0):m_value(val){} 

    int val() const {return m_value;} 

    static intObj mapFunction(const intObj &num){ 
     return intObj(num.val()); 
    } 

    static void reduceFunction(intObj &sum, const intObj &term){ 
     int x = sum.val(); 
     int y = term.val(); 
     sum = intObj(x+y); 
    } 

}; 

class myTest{ 
    public: 
    int getSum(QList<intObj> numbers); 

}; 

int main(int argc, char *argv[]) 
{ 
    QCoreApplication a(argc, argv); 
    QList<intObj> n; 

    for(int i = 0; i < 1000 ; i++){ 
     n.append(intObj(i)); 
    } 

    myTest m; 
    int sum = m.getSum(n); 
    return a.exec(); 
} 


int myTest::getSum(QList<intObj> numbers){ 
    auto sum = QtConcurrent::mappedReduced(numbers,&intObj::mapFunction,&intObj::reduceFunction); 
    return sum.result().val(); 
} 

このプログラムを改善する方法についてのご意見は、大歓迎です。

+0

ドキュメントを誤解しています - ラッパーオブジェクトと静的メソッドの両方を必要としません。 (私の答えに示されているように)静的メソッドを使用するか、ラッパー・オブジェクトに対してメンバー・メソッドを使用します(典型的な例は 'QString()'では '.length()')。 – Holt

関連する問題