c++ - Is there a type-erased function wrapper in the Standard Library that matches std::thread's constructor semantics? -
i need create non-template class¹ needs hold callable , arguments, in order invoke them @ later point.
since class modelling async execution, i'd give api , semantics matching ones of std::thread
/ std::async
:
class async { public: template <typename function, typename... args > explicit async(function&& f, args &&... args) { // perform (decay) copy of args, // store f , copy somewhere } void call() { // possibly called in different thread; // call function stored. no need return results } private: // data members? };
the first thing came mind use std::function<void()>
data member, , initialize std::bind
on arguments.
however, doesn't work: std::function
, std::bind
don't support move-only types, , std::bind
not work in terms of std::invoke
(and lot of magic, recursively resolve bindings).
am missing easy-to-reach solution available in standard library implement this, or should deploy own binder , type-erased function wrapper classes?
¹ long story short: class needs inherit base class virtual methods, making class template class cause usual code bloat , clashes due duplication of virtual tables , virtual methods appearing everywhere.
template<class t> t&& wrap_pm(t&& t) { return std::forward<t>(t); } template<class t, class u> auto wrap_pm(u t::* p) -> decltype(std::mem_fn(p)) { return std::mem_fn(p); } class async { public: template <typename function, typename... args > explicit async(function&& f, args &&... args) : fut(std::async(std::launch::deferred, [f=std::forward<function>(f)](auto&&... args) mutable { wrap_pm(std::move(f))(decltype(args)(args)...); }, std::forward<args>(args)...)) { } void call() { fut.get(); } private: std::future<void> fut; };
i make no promises efficiency.
Comments
Post a Comment