“使用”语句中的自/循环引用

时间:2019-10-07 18:56:56

标签: c++ forward-declaration

我尝试在程序中为动态变量定义一个变体类型,但似乎无法使它存储将其返回为类型的函数。

using Value = std::variant<Integer, Float, Function>;
using Function = std::function<Value()>;

这不会编译,因为需要在Function时定义Value,但是Function也取决于Value。我尝试通过将Function类型内联到变量模板列表中来解决此问题,但是似乎using语句无法引用自身或被向前声明。

到目前为止,我最好的解决方案是将Function定义为结构,以便我可以对其进行声明。这行得通,但似乎太黑了,所以我想知道是否有更好的方法?

struct Function;
// define Value
struct Function : std::function<Value()> {};

为澄清起见,示例中使用了std::function,因为我认为这样可以更轻松地展示我正在尝试做的事情,而对于我的hacky解决方案来说也是如此。如果可能的话,我更希望有一种使用普通函数指针的方法。

1 个答案:

答案 0 :(得分:3)

这是行不通的,因为您实际上要创建的内容是这样的:

std::variant<Integer, Float, std::function<std::variant<Integer, Float, std::function<std::variant<Integer, Float, std::function<std::variant<Integer, Float, std::function<std::variant<Integer, Float, std::function<std::variant<Integer, Float, std::function<std::variant<Integer, Float, std::function<std::variant<Integer, Float, std::function<std::variant<Integer, Float, std::function<std::variant<Integer, Float, std::function<std::variant<Integer, Float, std::function<...()>>()>>()>>()>>()>>()>>()>>()>>()>>()>>()>>;

因此,基本上,您在类型声明中具有无限递归。

您需要使用某种没有递归定义的类型来解决此问题,但是像您建议的那样直接使用转发的struct是不可行的,因为std::variant仅允许完整类型

您可以做的是向前声明您的struct,然后在您的std::unique_ptr<Function>中使用您选择的容器/包装器/智能指针(例如std::variant):

struct Function;
using Value = std::variant<Integer, Float, std::unique_ptr<Function>>;
struct Function : std::function<Value()> {};