And without any more messing around here is the generic version of the movable std::bind replacement.
- This version doesnt handle place holders yet.
- There is probably problems if you try to copy it
Update: I since added a placeholder version
here
#include <iostream>
#include <memory>
#include <utility>
#include <thread>
//A helper class for storage and stitching params together
template <typename A, typename ...Args>
struct MoveHelper : public MoveHelper<Args...>
{
A a_;
MoveHelper(A&& a, Args&& ...args) :
MoveHelper<Args...>(std::forward<Args>(args)...),
a_(std::forward<A>(a))
{}
template <typename Func, typename ...InArgs>
void call(Func& f, InArgs && ...args)
{
MoveHelper<Args...>::call(f,
std::forward(args)...,
std::move(a_));
}
};
//The helpers terminal case
template <typename A>
struct MoveHelper<A>
{
A a_;
MoveHelper(A&& a) :
a_(std::forward<A>(a))
{}
template <typename Func, typename ...InArgs>
void call(Func& f, InArgs && ...args)
{
f(std::forward<A>(args)...,
std::forward<A>(a_));
}
};
//the Main std::bind movable replacement
template <typename ...P>
class MovableBinder
{
typedef void (*F)(P&&...);
private:
F func_;
MoveHelper<P...> help_;
public:
MovableBinder(F func, P&& ...p) :
func_(func),
help_(std::forward<P>(p)...)
{}
MovableBinder(F func, P& ...p) :
func_(func),
help_(p...)
{}
~MovableBinder()
{}
void operator()()
{
help_.call(func_);
}
};
//And the test with threads.. the ultimate move only object...
void thread_core() {
std::this_thread::sleep_for(std::chrono::seconds(2));
}
void join_thread(std::thread&& t1)
{
std::cout << "Joining the thread....\n";
t1.join();
}
void join_threads(std::thread&& t1, std::thread&& t2)
{
std::cout << "Joining the threads....\n";
t1.join();
t2.join();
}
int main()
{
std::thread ta(thread_core);
std::thread tb(thread_core);
MovableBinder<std::thread, std::thread> movable_binder_threads(&join_threads, std::move(ta),std::move(tb));
movable_binder_threads();
std::thread tc(thread_core);
MovableBinder<std::thread> movable_binder_thread(&join_thread, std::move(tc));
movable_binder_thread();
}
No comments:
Post a Comment