1
目标:使函数调度按预期工作。最小的示例代码应该说明问题。我想支持以下任务:命名任务,它们在自己的类中实现,以及使用lambda指定的更简单的任务。理想情况下,任何可以转换为std::function<void (void)>
的应该可以工作。std :: enable_if和std :: shared_ptr
#include <iostream>
#include <memory>
#include <functional>
// A Base class for my tasks
class BaseTask
{
public:
virtual void blah() = 0;
};
// An important enough tasks that it gets to have its
// own class.
class NamedTask : public BaseTask
{
public:
virtual void blah()
{
std::cout << "Hey !" << std::endl;
}
};
// A wrapper around simpler tasks. (lambda)
class GenericTask : public BaseTask
{
public:
GenericTask(const std::function<void (void)> fct) :
fct_(fct) {}
virtual void blah() override
{
fct_();
}
private:
std::function<void (void)> fct_;
};
void enqueue(std::shared_ptr<BaseTask> t)
{
// store in queue.
// We'll just call it here for the sake of the example
t->blah();
}
template<typename Callable>
//typename std::enable_if<!std::is_base_of<BaseTask, Callable>::value>::type
//typename std::enable_if<!std::is_base_of<std::shared_ptr<BaseTask>, Callable>::value>::type
void enqueue(const Callable &c)
{
auto t = std::make_shared<GenericTask>(c);
t->blah();
}
int main()
{
auto named = std::make_shared<NamedTask>();
enqueue(named); // doesn't compile: tries to call the templated enqueue.
enqueue([]() -> bool { std::cout << "Lamda" << std::endl; });
}
问题:我不管理编写正确的enable_if
模板。示例中的注释行是我所尝试的。
- 第一个不起作用,因为赎回是
std::shared_ptr<NamedTask>
类型,这是不是BaseTask
的孩子。 - 第二个也失败了,大概是因为
std::shared_ptr<NamedTask>
不是来自std::shared_ptr<BaseTask>
。
我不知道'std :: is_convertible'。这正是我所期待的。感谢您提供可行的选择。 – Xaqq