Suppose I want to have a function double adapter(double), is there a general way to compose it with a boost::function<double(...)> functor to produce another boost::function<double(...)> functor2 where functor2(...) == adapter(functor(...))? In particular, it would be cool if there was a way to do this without using C++11.
edit To clarify, I'm interested in knowing if there's a way to write something that can handle any boost::function<double(...)>, i.e. ones that have different length signatures without having to copy and paste multiple times for 1, 2, 3, etc. arguments.
Without c++11, there are a significant number of complexities, including the varadic arguments and forwarding.
With C++11, it can be done, mostly by specializaing std::is_bind_expression. When this function object is used in a bind, it calls the function object that was stored with all of the arguments that were provided during the call to the bound function object. Note, this works with any function object, not just std::function.
This works with GCC 4.7.
#include <functional>
#include <utility>
#include <type_traits>
namespace detail
{
template<typename Func>
struct compose_functor
{
Func f;
explicit compose_functor(const Func& f) : f(f) {};
template<typename... Args>
auto operator()(Args&&... args) const -> decltype(f(std::forward<Args>(args)...))
{
return f(std::forward<Args>(args)...);
}
};
}
template<typename Func>
detail::compose_functor
<Func> compose(Func f)
{
return detail::compose_functor<Func>(f);
}
namespace std
{
template<typename T>
struct is_bind_expression< detail::compose_functor<T> > : true_type {};
}
#include <numeric>
int adapter(double d)
{
return (int)d;
}
int main()
{
std::function<int(double)> f1 = std::bind(adapter, compose(std::negate<double>()));
std::function<int(double, double)> f2 = std::bind(adapter, compose(std::plus<double>()));
// 1.5 -> -1.5 -> -1
std::cout << f1(1.5) << std::endl;
// 2.3+4.5 = 6.8 -> 6
std::cout << f2(2.3, 4.5) << std::endl;
}
Related
I was wondering if there is a lightweight version of std::function that works only for function pointers but doesnt have horrible :) syntax like regular function pointers.
Aka something like this:
int square(int x)
{
return x*x;
}
//...
function_ptr<int (int)> = square;
Ofc bind and all other fancy stuff std::function supports will fail, but I am ok with that, if I need std::function I will use it.
What you are asking for is for a template to tranform from signature to pointer to function to signature, that is, to add a pointer to the type. That is already done in the standard library:
std::add_pointer<X>::type
But since what you want is the nicer syntax, you can add a template alias:
template <typename T>
using ptr = typename std::add_pointer<T>::type;
Then you can use it directly in your container:
void f(int);
std::vector<ptr<void (int)>> v; // vector of pointers to functions taking `int`
v.push_back(&f);
Depending on the context you want to use this in, it could be as simple as auto and/or decltype:
#include <iostream>
int main()
{
auto f = square;
std::cout << f(5) << std::endl;
// define a type
using F = decltype(&square);
F g = square;
std::cout << g(5) << std::endl;
}
You can write an opaque wrapper if you do not want to use typedef directly. A prototype implementation using variadic templates is as follows. The same technique can be extended to other callable objects such as lambdas.
#include <iostream>
template<typename T>
struct function_ptr {};
template<class R, class... Args>
struct function_ptr<R(Args...)>{
typedef R (*funcType)(Args...);
function_ptr(funcType f) : _f(f) {}
funcType _f;
R operator()(Args... args) { return _f(args...);}
};
int square(int x) {
return x*x;
}
int main() {
function_ptr<int (int)> f = square;
std::cout << f(2) << std::endl;
}
Given a callable object ( a function ) a, and an argument b ( or a series of arguments ), I would like to deduce the type returned from f considering that f is overloaded with multiple signatures.
one of my many attempts is
#include <iostream>
#include <cstdint>
#include <string>
#include <functional>
#include <utility>
#include <typeinfo>
int foo(uint32_t a) { return ((a + 0) * 2); }
bool foo(std::string a) { return (a.empty()); }
/*template <typename A, typename B> auto bar(A a, B b) -> decltype(a(b)) {
return (a(b));
}*/
/*template <typename A, typename B> decltype(std::declval<a(b)>()) bar(A a, B b)
{
return (a(b));
}*/
template <typename A, typename B> void bar(std::function<A(B)> a, B b) {
std::cout << a(b) << "\n";
}
int main() {
// the following 2 lines are trivial and they are working as expected
std::cout << foo(33) << "\n";
std::cout << typeid(decltype(foo(std::string("nothing")))).name() << "\n";
std::cout << bar(foo, 33) << "\n";
//std::cout << bar(foo, std::string("Heinz")) << "\n";
return (0);
}
and 2 templates options are commented out and included in the previous code.
I'm using declval result_of auto decltype without any luck.
How does the overloading resolution process works at compile time ?
If anyone wants to know why I'm trying to get creative with this, is that I'm trying to implement some Currying in C++11 in a workable/neat way.
The problem is that you can't easily create a function object from an overload set: when you state foo or &foo (the function decays into a function pointer in most case, I think) you don't get an object but you get an overload set. You can tell the compiler which overload you want by either calling it or providing its signature. As far as I can tell, you don't want either.
The only approach I'm aware of is to turn your function into an actual function object which makes the problem go away:
struct foo_object
{
template <typename... Args>
auto operator()(Args&&... args) -> decltype(foo(std::forward<Args>(args)...)) {
return foo(std::forward<Args>(args)...);
}
};
With that wrapper which is unfortunately needed for each name, you can trivially deduce the return type, e.g.:
template <typename Func, typename... Args>
auto bar(Func func, Args&&... args) -> decltype(func(std::forward<Args>(args)...)) {
// do something interesting
return func(std::forward<Args>(args)...);
}
int main() {
bar(foo_object(), 17);
bar(foo_object(), "hello");
}
It doesn't quite solve the problem of dealing with overload sets but it gets reasonably close. I experimented with this idea, essentially also for the purpose of currying in the context of an improved system of standard library algorithms and I'm leaning towards the algorithms actually being function objects rather than functions (this is desirable for various other reasons, too; e.g., you don't need to faff about when you want to customize on algorithm with another one).
If foo is overloaded, you need to use the following:
#include <type_traits>
int foo(int);
float foo(float);
int main() {
static_assert(std::is_same<decltype(foo(std::declval<int>())), int>::value, "Nope.");
static_assert(std::is_same<decltype(foo(std::declval<float>())), float>::value, "Nope2.");
}
If it's not, then this will suffice:
#include <type_traits>
bool bar(int);
int main() {
static_assert(std::is_same<std::result_of<decltype(bar)&(int)>::type, bool>::value, "Nope3.");
}
Yes, it is verbose because you're trying to explicitly extract what implicit ad-hoc overloading does for you.
This is actually already implemented for you std::result_of. Here is a possible implementation
template<class>
struct result_of;
// C++11 implementation, does not satisfy C++14 requirements
template<class F, class... ArgTypes>
struct result_of<F(ArgTypes...)>
{
typedef decltype(
std::declval<F>()(std::declval<ArgTypes>()...)
) type;
};
I have a problem when invoking nested std::bind expressions. The following code demonstrates the problem. It fails to compile with libc++, but works with boost:
#define BOOST 0
#if BOOST
#include <boost/function.hpp>
#include <boost/bind.hpp>
using boost::function;
using boost::bind;
#else
#include <functional>
using std::function;
using std::bind;
using std::placeholders::_1;
#endif
int sum(int a, int b) { return a+b; }
// works
template <typename F>
int yeah(F f, int c)
{
return f(c);
}
// breaks with libc++
template <typename F>
int nope(F f, int c)
{
return bind(f, c)();
}
// fixes the problem
template <typename F>
int fix1(F f, int c)
{
function<int(int)> g = f;
return bind(g, c)();
}
template <typename F>
class protect_t
{
public:
typedef typename F::result_type result_type;
explicit protect_t(F f): f_(f) {}
template <typename... Args>
result_type operator()(Args&&... args)
{
return f_(std::forward<Args>(args)...);
}
private:
F f_;
};
template <typename F>
protect_t<F> protect(F f)
{
return protect_t<F>(f);
}
// compilation fails with libc++
template <typename F>
int fix2(F f, int c)
{
return bind(protect(f), c)();
// F copy(f); // fails due to this!
}
#include <iostream>
int main()
{
std::cout << yeah(bind(sum, _1, 4), 5) << std::endl; // works
std::cout << nope(bind(sum, _1, 4), 5) << std::endl; // breaks
std::cout << fix1(bind(sum, _1, 4), 5) << std::endl; // fixes
std::cout << fix2(bind(sum, _1, 4), 5) << std::endl; // doesn't compile
}
Wrapping the bind expression in a std::function (see fix1) remedies the problem, albeit by sacrificing speed due to run-time polymorphism disabling inlining (haven't measured it though).
Wrapping the bind expression in protect_t (see fix2) is inspired by boost::protect, however, compilation with libc++ fails due to bind expressions not being copyable. Which makes me wonder why wrapping them in std::function works anyway.
Any idea how to solve this problem? What's wring with std::bind anyway? First I thought the problem is related to eager evaluation of bind expressions dictated by the C++11 standard (see here), but that would not be a problem here, would it?
The standard says that any callable can be wrapped using std::bind, including those produced by a preceding call to std::bind. Your problem is caused by a deficiency in the implementation of the standard library you're using, the solution is either to upgrade or, if this bug isn't still fixed, to switch to a different implementation.
I'm looking at the following problem:
I get strings that are formatted like this:
functionname_parameter1_parameter2_parameter3
otherfunctionname_parameter1_parameter2
.
.
.
and i would like to call the function with the given parameters.
So let's say i have a function test:
void test(int x, float y, std::string z) {}
and i get a message:
test_5_2.0_abc
then i would like the function test to be automatically invoked like this:
test(5, 2.0, "abc");
Do you have any hints on how to accomplish this in C++?
Update: Updated stream_function to fix the argument-evaluation-order problem #Nawaz mentioned in the comments, and also removed the std::function for improved efficiency. Note that the evaluation-order fix only works for Clang, as GCC doesn't follow the standard here. An example for GCC, with manual order-enforcement, can be found here.
This is generally not that easy to accomplish. I wrote a little wrapper class around std::function once that extracts the arguments from a std::istream. Here's an example using C++11:
#include <map>
#include <string>
#include <iostream>
#include <sstream>
#include <functional>
#include <stdexcept>
#include <type_traits>
// for proper evaluation of the stream extraction to the arguments
template<class R>
struct invoker{
R result;
template<class F, class... Args>
invoker(F&& f, Args&&... args)
: result(f(std::forward<Args>(args)...)) {}
};
template<>
struct invoker<void>{
template<class F, class... Args>
invoker(F&& f, Args&&... args)
{ f(std::forward<Args>(args)...); }
};
template<class F, class Sig>
struct stream_function_;
template<class F, class R, class... Args>
struct stream_function_<F, R(Args...)>{
stream_function_(F f)
: _f(f) {}
void operator()(std::istream& args, std::string* out_opt) const{
call(args, out_opt, std::is_void<R>());
}
private:
template<class T>
static T get(std::istream& args){
T t; // must be default constructible
if(!(args >> t)){
args.clear();
throw std::invalid_argument("invalid argument to stream_function");
}
return t;
}
// void return
void call(std::istream& args, std::string*, std::true_type) const{
invoker<void>{_f, get<Args>(args)...};
}
// non-void return
void call(std::istream& args, std::string* out_opt, std::false_type) const{
if(!out_opt) // no return wanted, redirect
return call(args, nullptr, std::true_type());
std::stringstream conv;
if(!(conv << invoker<R>{_f, get<Args>(args)...}.result))
throw std::runtime_error("bad return in stream_function");
*out_opt = conv.str();
}
F _f;
};
template<class Sig, class F>
stream_function_<F, Sig> stream_function(F f){ return {f}; }
typedef std::function<void(std::istream&, std::string*)> func_type;
typedef std::map<std::string, func_type> dict_type;
void print(){
std::cout << "print()\n";
}
int add(int a, int b){
return a + b;
}
int sub(int a, int b){
return a - b;
}
int main(){
dict_type func_dict;
func_dict["print"] = stream_function<void()>(print);
func_dict["add"] = stream_function<int(int,int)>(add);
func_dict["sub"] = stream_function<int(int,int)>(sub);
for(;;){
std::cout << "Which function should be called?\n";
std::string tmp;
std::cin >> tmp;
auto it = func_dict.find(tmp);
if(it == func_dict.end()){
std::cout << "Invalid function '" << tmp << "'\n";
continue;
}
tmp.clear();
try{
it->second(std::cin, &tmp);
}catch(std::exception const& e){
std::cout << "Error: '" << e.what() << "'\n";
std::cin.ignore();
continue;
}
std::cout << "Result: " << (tmp.empty()? "none" : tmp) << '\n';
}
}
Compiles under Clang 3.3 and works as expected (small live example).
Which function should be called?
a
Invalid function 'a'
Which function should be called?
add
2
d
Error: 'invalid argument to stream_function'
Which function should be called?
add
2
3
Result: 5
Which function should be called?
add 2 6
Result: 8
Which function should be called?
add 2
6
Result: 8
Which function should be called?
sub 8 2
Result: 6
It was fun to hack that class together again, hope you enjoy. Note that you need to modify the code a little to work for your example, since C++ IOstreams have whitespace as delimiter, so you'd need to replace all underscores in your message with spaces. Should be easy to do though, after that just construct a std::istringstream from your message:
std::istringstream input(message_without_underscores);
// call and pass 'input'
You pretty much can't, C++ doesn't have any kind of reflection on functions.
The question then is how close you can get. An interface like this is pretty plausible, if it would suit:
string message = "test_5_2.0_abc";
string function_name = up_to_first_underscore(message);
registered_functions[function_name](message);
Where registered_functions is a map<string,std::function<void,string>>, and you have to explicitly do something like:
registered_functions["test"] = make_registration(test);
for each function that can be called in this way.
make_registration would then be a fairly hairy template function that takes a function pointer as a parameter and returns a std::function object that when called splits the string into chunks, checks that there are the right number there, converts each one to the correct parameter type with a boost::lexical_cast, and finally calls the specified function. It would know the "correct type" from the template argument to make_registration -- to accept arbitrarily many parameters this would have to be a C++11 variadic template, but you can fake it with:
std::function<void,string> make_registration(void(*fn)(void));
template <typename T>
std::function<void,string> make_registration(void(*fn)(T));
template <typename T, U>
std::function<void,string> make_registration(void(*fn)(T, U));
// etc...
Dealing with overloads and optional parameters would add further complication.
Although I don't know anything about them, I expect that there are C++ support frameworks out there for SOAP or other RPC protocols, that might contain some relevant code.
What you are looking for is reflection. And it is not possible in C++. C++ is designed with speed in mind. If you require inspection of a library or code and then identify the types in it and invoke methods associated with those types (usually classes) then I am afraid it is not possible in C++.
For further reference you can refer to this thread.
How can I add reflection to a C++ application?
http://en.wikibooks.org/wiki/C%2B%2B_Programming/RTTI
Why does C++ not have reflection?
You could parse the string, separate the arguments and send them to the function with no problem, but what you cannot do is reference the function with its name on a string, because the function doesn't have a name anymore at runtime.
You could have a if-else if chain that checks for the function name, and then parse the arguments and call the specific function.
I modified #Xeo's code to work with gcc properly, so it ensures the parameters are pulled in the right order. I'm only posting this since it took me a while to understand the original code and splice in the order-enforcement. Full credit should still go to #Xeo. If I find anything wrong with my implementation I'll come back and edit, but thus far in my testing I haven't seen any problems.
#include <map>
#include <string>
#include <iostream>
#include <sstream>
#include <functional>
#include <stdexcept>
#include <type_traits>
#include <tuple>
template<class...> struct types{};
// for proper evaluation of the stream extraction to the arguments
template<class ReturnType>
struct invoker {
ReturnType result;
template<class Function, class... Args>
invoker(Function&& f, Args&&... args) {
result = f(std::forward<Args>(args)...);
}
};
template<>
struct invoker<void> {
template<class Function, class... Args>
invoker(Function&& f, Args&&... args) {
f(std::forward<Args>(args)...);
}
};
template<class Function, class Sig>
struct StreamFunction;
template<class Function, class ReturnType, class... Args>
struct StreamFunction<Function, ReturnType(Args...)>
{
StreamFunction(Function f)
: _f(f) {}
void operator()(std::istream& args, std::string* out_opt) const
{
call(args, out_opt, std::is_void<ReturnType>());
}
private:
template<class T>
static T get(std::istream& args)
{
T t; // must be default constructible
if(!(args >> t))
{
args.clear();
throw std::invalid_argument("invalid argument to stream_function");
}
return t;
}
//must be mutable due to const of the class
mutable std::istream* _args;
// void return
void call(std::istream& args, std::string*, std::true_type) const
{
_args = &args;
_voidcall(types<Args...>{});
}
template<class Head, class... Tail, class... Collected>
void _voidcall(types<Head, Tail...>, Collected... c) const
{
_voidcall<Tail...>(types<Tail...>{}, c..., get<Head>(*_args));
}
template<class... Collected>
void _voidcall(types<>, Collected... c) const
{
invoker<void> {_f, c...};
}
// non-void return
void call(std::istream& args, std::string* out_opt, std::false_type) const {
if(!out_opt) // no return wanted, redirect
return call(args, nullptr, std::true_type());
_args = &args;
std::stringstream conv;
if(!(conv << _call(types<Args...>{})))
throw std::runtime_error("bad return in stream_function");
*out_opt = conv.str();
}
template<class Head, class... Tail, class... Collected>
ReturnType _call(types<Head, Tail...>, Collected... c) const
{
return _call<Tail...>(types<Tail...>{}, c..., get<Head>(*_args));
}
template<class... Collected>
ReturnType _call(types<>, Collected... c) const
{
return invoker<ReturnType> {_f, c...} .result;
}
Function _f;
};
template<class Sig, class Function>
StreamFunction<Function, Sig> CreateStreamFunction(Function f)
{
return {f};
}
typedef std::function<void(std::istream&, std::string*)> StreamFunctionCallType;
typedef std::map<std::string, StreamFunctionCallType> StreamFunctionDictionary;
This also works with Visual Studio 2013, have not tried earlier versions.
I am trying to use a lambda to pass in place of a function pointer but VS2010 can't seem to convert it. I have tried using std::function like this and it crashes and I have no idea if I am doing this right!
#include <windows.h>
#include <conio.h>
#include <functional>
#include <iostream>
#include <concrt.h>
void main()
{
std::function<void(void*)> f = [](void*) -> void
{
std::cout << "Hello\n";
};
Concurrency::CurrentScheduler::ScheduleTask(f.target<void(void*)>(), 0);
getch();
}
It seems strange to me that the compiler can't convert such a lambda to a simple function pointer as it captures no variables - also in the case that it did I wonder what can be done.
Is the type of each lambda unique? So I could hack around with a template function using the lambdas' type as a template argument to generate a unique static function that could be called instead and hopefully optimised out?
UPDATED
The below seems to work but is it safe?
#include <windows.h>
#include <conio.h>
#include <iostream>
#include <concrt.h>
template<typename Signature>
struct Bind
{
static Signature method;
static void Call(void* parameter)
{
method(parameter);
}
};
template<typename Signature>
Signature Bind<Signature>::method;
template<typename Signature>
void ScheduleTask(Signature method)
{
Bind<Signature>::method = method;
Concurrency::CurrentScheduler::ScheduleTask(&Bind<Signature>::Call,0);
}
void main()
{
ScheduleTask
(
[](void*)
{
std::cout << "Hello";
}
);
ScheduleTask
(
[](void*)
{
std::cout << " there!\n";
}
);
getch();
}
UPDATED AGAIN
So with the help given I have come up with the shorter:
template<typename Signature>
void (*LambdaBind(Signature))(void*)
{
struct Detail
{
static void Bind(void* parameter)
{
Signature method;
method(parameter);
}
};
return &Detail::Bind;
}
This can be used to wrap a lambda with no closure of void(*)(void*) into the equivalent function pointer. It appears that this will become unnecessary in a later version of VS2010.
So how to get this to work for a lambda with closures?
UPDATED AGAIN!
Works for closures in VS2010 - no idea if it's 'safe' though...
template<typename Signature>
struct Detail2
{
static std::function<void(void*)> method;
static void Bind(void* parameter)
{
method(parameter);
}
};
template<typename Signature>
std::function<void(void*)> Detail2<Signature>::method;
template<typename Signature>
void (*LambdaBind2(Signature method))(void*)
{
Detail2<Signature>::method = method;
return &Detail2<Signature>::Bind;
}
This feature of lambda's was added after VS2010 implemented them, so they don't exist in it yet.
Here's a possible generic work-around, very untested:
#include <functional>
#include <iostream>
namespace detail
{
// helper specializations,
// define forwarding methods
template <typename Lambda, typename Func>
struct lambda_wrapper;
#define DEFINE_OPERATOR \
typedef decltype(&call) function_type; \
operator function_type(void) const \
{ \
return &call; \
}
template <typename Lambda, typename C, typename R>
struct lambda_wrapper<Lambda, R (C::*)(void) const>
{
static R call(void)
{
Lambda x;
return x();
}
DEFINE_OPERATOR
};
template <typename Lambda, typename C, typename R,
typename A0>
struct lambda_wrapper<Lambda, R (C::*)(A0) const>
{
static R call(A0&& p0)
{
Lambda x;
return x(std::forward<A0>(p0));
}
DEFINE_OPERATOR
};
// and so on
#undef DEFINE_OPERATOR
}
// wraps a lambda and provides
// a way to call it statically
template <typename Lambda>
struct lambda_wrapper :
detail::lambda_wrapper<Lambda, decltype(&Lambda::operator())>
{};
template <typename Lambda>
lambda_wrapper<Lambda> wrap_lambda(const Lambda&)
{
return lambda_wrapper<Lambda>();
}
int main(void)
{
auto l = [](){ std::cout << "im broked :(" << std::endl; };
std::function<void(void)> f = wrap_lambda(l);
f();
}
Let me know if any part is confusing.
If scheduling lambdas/function objects in Concurrency::CurrentScheduler is what you want, it may be worth your while looking at ConcRT Sample Pack v0.32 here
The task_scheduler struct can schedule lambdas asynchronously, but be advised, passing by reference may cause bad things to happen (since we are talking about asynchronous scheduling without a join/wait, a reference on the stack may no longer be valid at time of task execution!)