c++ - 继承自 boost::variant 和模板化 AST

标签 c++ boost boost-variant

以下代码crashes GCC并且无法使用 Clang 进行编译。有什么问题吗?

#include <boost/variant.hpp>
#include <array>
#include <iostream>


template<class Node>
struct wrapper1;
template<class Node>
struct wrapper2;

struct ast_node;
using ast_node_base = boost::variant<boost::recursive_wrapper<wrapper1<ast_node>>, boost::recursive_wrapper<wrapper2<ast_node>>>;

struct ast_node : ast_node_base
{
    using ast_node_base::ast_node_base;
};

template<class Node>
struct wrapper1
{
    std::array<Node, 1> children;
};

template<class Node>
struct wrapper2
{
    std::array<Node, 2> children;
};


int main()
{
    ast_node node;
    std::cout << "done\n";
}

最佳答案

您在构造函数中获得无限递归。

第一个变体成员本身包含 1 个节点的聚合。因此,默认构造的 ast_node 将递归初始化 wrapper1,它会在堆栈溢出时触底。

最简单的修复:

Live On Coliru

#include <array>
#include <boost/variant.hpp>
#include <iostream>

template <class Node> struct wrapper1;
template <class Node> struct wrapper2;

struct nil {};
struct ast_node;
using ast_node_base = boost::variant<nil, boost::recursive_wrapper<wrapper1<ast_node> >, boost::recursive_wrapper<wrapper2<ast_node> > >;

struct ast_node : ast_node_base {
    using ast_node_base::ast_node_base;
};

template <class Node> struct wrapper1 { std::array<Node, 1> children; };
template <class Node> struct wrapper2 { std::array<Node, 2> children; };

int main() {
    ast_node node;
    std::cout << "done\n";
}

关于c++ - 继承自 boost::variant 和模板化 AST,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38950728/

相关文章:

c++ - 如何测试我的迭代器是否等于一个位置

c++ - C++ 中的返回数组

c++ - 无法创建 C++ ruby​​ 扩展

c++ - Boost.Tokenizer 如何不从标记中删除分隔符

c++ - 使用 Boost Variants 在 C++ 中表示 JSON 数据

c++ - 如何在包含类型的变体上使用比较运算符?

c++ - 从 boost::variant 获取 int 生成段错误

c++ - 当我定义 UNICODE 和/或 _UNICODE 时,非 unicode API 函数会发生什么情况?

c++ - 使用多个定界符拆分字符串并将其保存到 vector 中

c++ - 如何修改 boost 多边形?