Forums
New posts
Search forums
Members
Current visitors
Log in
Register
What's new
Search
Search
Search titles only
By:
New posts
Search forums
Menu
Log in
Register
Install the app
Install
Forums
Archive
Archive
C++
boost::lambda
JavaScript is disabled. For a better experience, please enable JavaScript in your browser before proceeding.
You are using an out of date browser. It may not display this or other websites correctly.
You should upgrade or use an
alternative browser
.
Reply to thread
Message
[QUOTE="Steve Hicks, post: 2566611"] Here is my attempt. This is the smallest example I could throw together that (a) compiles, and (b) does something interesting. namespace { // This is basically the placeholder class identity_functor { public: // Return type template<typename arg1_type> struct return_type { typedef arg1_type type; }; // Constructor (use default) // Operator template<typename arg1_type> typename return_type<arg1_type>::type operator()(arg1_type s) { return s; } }; // Constant functor template<typename T> class const_functor { T _data; public: // Return type template<typename arg1_type> struct return_type { typedef T type; }; // Constructor (implicit) const_functor(T __data) : _data(__data) { } // Operator template<typename arg1_type> typename return_type<arg1_type>::type operator()(arg1_type) { return _data; } }; // Helper function (I shouldn't need this) template <typename T> const_functor<T> constant(T t) { return const_functor<T>(t); } // Sum functor template <typename left_type,typename right_type> class sum_functor { left_type _left; right_type _right; public: // Return type template <typename arg1_type> struct return_type { typedef typename left_type::template return_type<arg1_type>::type type; }; // Constructor sum_functor(left_type __left,right_type __right) : _left(__left), _right(__right) { } // Operator template<typename arg1_type> typename return_type<arg1_type>::type operator()(arg1_type s) { return _left(s)+_right(s); } }; // + operator template<typename left_type,typename right_type> sum_functor<left_type,right_type> operator+(left_type _left,right_type _right) { return sum_functor<left_type,right_type>(_left,_right); } // Placeholders identity_functor X; } int main() { std::cout << (X+constant(1))(5) << std::endl; return 0; } It appears to me that this is basically how boost::lambda works. The trickiest part seems to be determining the return types. I just chose to use the left-hand argument of addition to determine the type, although it would be better to make a two-argument template which picked the more precise type of the two. We just pass around arg1_type as a template argument which is the type of the placeholder. Several caveats: First, I had to put it into an unnamed namespace because I use global templates to overload the operator. I wish I could have a lambda_functor base class, but we can't have the templated operator() be virtual (and we probably don't want to use inheritance anyway, since it would slow things down). One downside to this is the explicit constant() call which is required so that we operate on two functor objects. Second, there's a lot of issues with type traits. The reason I chose operator+ as an example is because streams require references, while these are all values. To get any more complicated, we'd need to have to get into casting the template types into references and consts, and I really don't understand that at all. If anyone has further comments, I would really appreciate your input. [/QUOTE]
Verification
Post reply
Forums
Archive
Archive
C++
boost::lambda
Top