2010-11-29 7 views
2

は、以下の簡単な例を見てください:このブースト::ラムダで私を助け:: if_then式をファンクタを呼び出す

#include <vector> 
#include <string> 
#include <algorithm> 
#include <boost/lambda/lambda.hpp> 
#include <boost/lambda/bind.hpp> 
#include <boost/lambda/if.hpp> 

using namespace boost::lambda; 
namespace bl = boost::lambda; 

using namespace std; 

struct Item 
{ 
    string sachNr; 
    int ist; 
    int soll; 
}; 

struct Printer 
{ 
    void operator()(const Item &item) 
    { 
     m_erg += item.sachNr; 
    } 

    operator string() 
    { 
     return m_erg; 
    } 

private: 

    string m_erg; 
}; 

void TestFunction() 
{ 
    vector<Item> pickItems; 

    string result = for_each(pickItems.begin(), pickItems.end(), 
     bl::if_then(bl::bind(&Item::ist, bl::_1) == bl::bind(&Item::soll, bl::_1), 
     Printer())); 
} 

にErrorMessage(GCC)

/TestCpp-build-desktop/../TestCpp/ctest.cpp:52: error: no matching function for call to ‘if_then(const boost::lambda::lambda_functor<boost::lambda::lambda_functor_base<boost::lambda::relational_action<boost::lambda::equal_action>, boost::tuples::tuple<boost::lambda::lambda_functor<boost::lambda::lambda_functor_base<boost::lambda::action<2, boost::lambda::function_action<2, boost::lambda::detail::unspecified> >, boost::tuples::tuple<int Item::* const, const boost::lambda::lambda_functor<boost::lambda::placeholder<1> >, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type> > >, boost::lambda::lambda_functor<boost::lambda::lambda_functor_base<boost::lambda::action<2, boost::lambda::function_action<2, boost::lambda::detail::unspecified> >, boost::tuples::tuple<int Item::* const, const boost::lambda::lambda_functor<boost::lambda::placeholder<1> >, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type> > >, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type, boost::tuples::null_type> > >, Printer)’ 

任意のヒント何が間違っていますそのコードで?

item.soll == item.istの項目については、プリンタファンクタを呼び出すことになっています。

ありがとうございました!

+0

わからないが、別の構文( 'IF_(状態を)しようとすると、[機能]'別の問題を明らかに:for_each 'にファンクタをちょうどPrinterオブジェクトを含まない代替手段を提供します'は' Printer'ではなくboost lambdaオブジェクトなので、文字列への変換はとにかく起こることは期待できません - すでにファンクタを書いているので、もう少し作業してみてはいかがですか? – visitor

+0

あるいは、BOOST_FOREACH IMOはfor_eachを得るのは無意味です。 – visitor

+0

はい、私はBOOST_FOREACHで動作するように変更しました。それにも関わらず私はそれをw上記のサンプルコードでは(常に新しいものを学習しようとしています) – nabulke

答えて

2

ronagが正しく、ブーストのラムダの言及は、 "彼らはすべてラムダファンクタを引数とし、voidを返します。

代替構文(bl::if_(condition)[function])には、λファンクタが必要ないようです。

しかし、別の大きな問題は、for_eachが、プリンタではなく、ブーストラムダオブジェクトであるファンクタを返すことです。したがって、とにかく蓄積された文字列を取得する方法はありません。

あなたはそれがこのようなもので動作するようになるかもしれない。しかし

#include <vector> 
#include <string> 
#include <algorithm> 
#include <boost/lambda/lambda.hpp> 
#include <boost/lambda/bind.hpp> 
#include <boost/lambda/if.hpp> 

using namespace boost::lambda; 
namespace bl = boost::lambda; 

using namespace std; 

struct Item 
{ 
    string sachNr; 
    int ist; 
    int soll; 
}; 

struct Printer 
{ 
    typedef void result_type; 
    void operator() (const Item &item, std::string& s) const 
    { 
     s += item.sachNr; 
    } 
}; 

void TestFunction() 
{ 
    vector<Item> pickItems; 

    string result; 
    for_each(pickItems.begin(), pickItems.end(), 
     bl::if_then(
      bl::bind(&Item::ist, bl::_1) == bl::bind(&Item::soll, bl::_1), 
      bl::bind(Printer(), bl::_1, boost::ref(result)) 
     ) 
    ); 
} 

void TestFunction() 
{ 
    vector<Item> pickItems; 
    string result; 
    BOOST_FOREACH(const Item& item, pickItems) { 
     if (item.ist == item.soll) 
      result += item.sachNr; 
    } 

} 

はあなたが望む結果を得るためにずっと簡単になります。 for_eachは事実上何も役に立たないので、私はそれを些細な事のためだけに使うのではない。

1

これを試してみてください:

Printer printer; 
std::for_each(pickItems.begin(), pickItems.end(), bl::if_then(bl::bind(&Item::ist, bl::_1) == bl::bind(&Item::soll, bl::_1), bl::bind(&Printer::operator(), &printer, bl::_1))); 

BL :: if_thenは、任意のファンクタを受け付けないように私には思える、それはlambda_functorにする必要があります。

1

正解は既に提供されています。この特定のエラーについて

std::string s; 
for_each(
    pickItems.begin(), pickItems.end(), 
    bl::if_ (bl::bind(&Item::ist, bl::_1) == bl::bind(&Item::soll, bl::_1)) 
    [ 
     s += bl::bind(&Item::sachNr, bl::_1) 
    ] 
); 
関連する問題