Re: [Boost-users] Getting the argument types from a function type
Hello Kirit,
to solve your specific problem, you could just do without Boost.function and also use templates for operator():
template
I've been playing around with a few functional programming idioms in C++ using Boost.function and Boost.lambda and was wondering if it was possible to fetch out the argument type (i.e. int) from a type like this:
void (*somefunc)( int )
It looks to me like boost::function<> might be doing something along these lines.
I've been working on a version of 'with' for use in initialising lists etc. At the moment you need to do this:
std::list< int > list1; list1.push_back( 3 ); list1.push_back( 1 ); list1.push_back( 4 );
But using 'with' you can do this:
with( list2, &std::list< int >::push_back )( 3 )( 1 )( 4 )( 1 )( 5 );
The implementation I have right now is fairly simple:
template< typename F > struct with_binder { with_binder( F f ) : m_f( f ) { } const with_binder &operator()( int i ) const { m_f( i ); return *this; } private: F m_f; }; template< typename O, typename F > inline with_binder< boost::function< void ( int ) > > with( O &o, F f ) { return with_binder< boost::function< void ( int ) > >( boost::lambda::bind( f, &o, boost::lambda::_1 ) ); }
But the 'int' argument type is hard coded. I could have it as the first template parameter to 'with' and simply require that it is given when using 'with', but it would neater if it could be derived from the type 'F' in 'with'. Clearly to be more generally useful it also needs to be extended for multiple parameters.
K
_______________________________________________ Boost-users mailing list Boost-users@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/boost-users
Why not just use boost::function_traits ? That's what they're for. http://www.boost.org/doc/html/boost_typetraits/reference.html#boost_typetrai... Damien
Hello Kirit,
to solve your specific problem, you could just do without Boost.function and also use templates for operator():
template
class with_binder { C& m_this; F m_fn; public: with_binder(C& ref, F fn) : m_this(ref), m_fn(fn) { } // one parameter template <typename T1> const with_binder
& operator()(T1& v1) const { (m_this.*m_fn)(v1); return *this; } template <typename T1> const with_binder & operator()(const T1& v1) const { (m_this.*m_fn)(v1); return *this; } // two parameters template
const with_binder & operator()(T1& v1, T2& v2) const { (m_this.*m_fn)(v1, v2); return *this; } template const with_binder & operator()(const T1& v1, const T2& v2) const { (m_this.*m_fn)(v1, v2); return *this; } // ... and so on ...
};
template
with_binder with(C& ref, F fn) { return with_binder (ref,fn); } Regards, Benjamin
I've been playing around with a few functional programming idioms in C++ using Boost.function and Boost.lambda and was wondering if it was possible to fetch out the argument type (i.e. int) from a type like this:
void (*somefunc)( int )
It looks to me like boost::function<> might be doing something along these lines.
I've been working on a version of 'with' for use in initialising lists etc. At the moment you need to do this:
std::list< int > list1; list1.push_back( 3 ); list1.push_back( 1 ); list1.push_back( 4 );
But using 'with' you can do this:
with( list2, &std::list< int >::push_back )( 3 )( 1 )( 4 )( 1 )( 5 );
The implementation I have right now is fairly simple:
template< typename F > struct with_binder { with_binder( F f ) : m_f( f ) { } const with_binder &operator()( int i ) const { m_f( i ); return *this; } private: F m_f; }; template< typename O, typename F > inline with_binder< boost::function< void ( int ) > > with( O &o, F f ) { return with_binder< boost::function< void ( int ) > >( boost::lambda::bind( f, &o, boost::lambda::_1 ) ); }
But the 'int' argument type is hard coded. I could have it as the first template parameter to 'with' and simply require that it is given when using 'with', but it would neater if it could be derived from the type 'F' in 'with'. Clearly to be more generally useful it also needs to be extended for multiple parameters.
K
_______________________________________________ Boost-users mailing list Boost-users@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/boost-users
Boost-users mailing list Boost-users@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/boost-users
(Reply to two posts here) damien@khubla.com wrote:
Why not just use boost::function_traits ? That's what they're for.
http://www.boost.org/doc/html/boost_typetraits/reference.html#boost_typetrai...
They don't work with function pointers and I'm binding to a pointer to member function.
Damien
Hello Kirit,
to solve your specific problem, you could just do without Boost.function and also use templates for operator():
This looks like a great way to solve this specific problem. I've never seen a use for .* before. I think I understand what's going on with it now.
template
class with_binder { C& m_this; F m_fn; public: with_binder(C& ref, F fn) : m_this(ref), m_fn(fn) { } // one parameter template <typename T1> const with_binder
& operator()(T1& v1) const { (m_this.*m_fn)(v1); return *this; } template <typename T1> const with_binder & operator()(const T1& v1) const { (m_this.*m_fn)(v1); return *this; } // two parameters template
const with_binder & operator()(T1& v1, T2& v2) const { (m_this.*m_fn)(v1, v2); return *this; } template const with_binder & operator()(const T1& v1, const T2& v2) const { (m_this.*m_fn)(v1, v2); return *this; } // ... and so on ...
};
template
with_binder with(C& ref, F fn) { return with_binder (ref,fn); } Regards, Benjamin
I've been playing around with a few functional programming idioms in C++ using Boost.function and Boost.lambda and was wondering if it was possible to fetch out the argument type (i.e. int) from a type like this:
void (*somefunc)( int )
It looks to me like boost::function<> might be doing something along these lines.
I've been working on a version of 'with' for use in initialising lists etc. At the moment you need to do this:
std::list< int > list1; list1.push_back( 3 ); list1.push_back( 1 ); list1.push_back( 4 );
But using 'with' you can do this:
with( list2, &std::list< int >::push_back )( 3 )( 1 )( 4 )( 1 )( 5 );
The implementation I have right now is fairly simple:
template< typename F > struct with_binder { with_binder( F f ) : m_f( f ) { } const with_binder &operator()( int i ) const { m_f( i ); return *this; } private: F m_f; }; template< typename O, typename F > inline with_binder< boost::function< void ( int ) > > with( O &o, F f ) { return with_binder< boost::function< void ( int ) > >( boost::lambda::bind( f, &o, boost::lambda::_1 ) ); }
But the 'int' argument type is hard coded. I could have it as the first template parameter to 'with' and simply require that it is given when using 'with', but it would neater if it could be derived from the type 'F' in 'with'. Clearly to be more generally useful it also needs to be extended for multiple parameters.
K
Kirit Sælensminde wrote:
(Reply to two posts here)
damien@khubla.com wrote:
Why not just use boost::function_traits ? That's what they're for.
http://www.boost.org/doc/html/boost_typetraits/reference.html#boost_typetrai...
They don't work with function pointers and I'm binding to a pointer to member function.
In case you're using the CVS HEAD you might want to take a look at $(BOOST_ROOT)/boost/libs/function_types/doc/html/index.html
... ...
Please remove unnecessary quoted text from your posts, BTW (so messages can easily be found in the archives and become more readable). http://www.boost.org/more/discussion_policy.htm#effective Regards, Tobias
participants (4)
-
Benjamin Winkler
-
damien@khubla.com
-
Kirit Sælensminde
-
Tobias Schwinger