如何包装 Callable 使其成为常规类型?

How to wrap Callable to make it regular type?

我正在编写迭代器外观,但似乎我的迭代器甚至会违反 Alexander Stepanov 的基本 Iterator concept. The problem is that the iterator accepts any Callable, which might render fundamental operations on Regular Types ill formed. I'm following definition presented。这是声明:

template<typename Callable, typename Iterator>
class transform_iterator 

问题:如何包装可调用对象使其成为常规类型?

实际上我只需要包装器:

而不是一般的常规类型。

我的第一次尝试:换成std::optional<>:

template <typename T>
class regular_box
{
    std::experimental::optional<T> value;
public:

//constructors, operator=

    template <typename ... ArgTypes>
    auto operator()(ArgTypes&& ... args)
    {
        return callable.value()(std::forward<ArgTypes>(args)...);
    }
};

但是它并没有解决赋值问题,因为如果 Callable 不可复制赋值,那么 regular_box 也不会被复制赋值。

计划 Bstd::function<>。虽然我想尽可能推迟它。

我可以进行多级回退,但找不到比这更好的解决方案。

有一些方法可以得到这样的类型:

  1. 引用并存储在reference_wrapper。
    参考显然是可复制构造的。

  2. 如果您想拥有回调并管理生命周期,请将其存储在shared_ptr。
    这会增加很多开销,但它确实有效。