如何在C++中整理树数据结构的前向引用

How to sort out forward references for a tree data structure in C++

本文关键字:数据结构 引用 C++      更新时间:2023-10-16

在C++11中,我想定义一个树数据结构,其中每个节点都有一组键(std::string(,每个键都与两个值相关联:另一个std::string,以及指向树中子节点的指针。 这样做的自然方法似乎是使一个节点成为一个std::unordered_map,具有std::string键和值,这些值是std::stringstd::pair和指向子节点的指针。 目前,我有这个:

struct tree_node;
typedef std::pair<std::string, tree_node *> tree_value;
struct tree_node {
    std::unordered_map<std::string, tree_value> key_val_map;
};

令人讨厌的是这一切中间的struct;当我使用这些数据结构时,我不得不不断通过key_val_map迈出额外的一步。 我希望tree_node简单地被typedef为有问题的std::unordered_map。 这似乎是可能的,因为tree_value仅指指针tree_node;我应该能够以某种方式向前声明tree_node以便我可以定义tree_value. 不过,我找不到这样做的方法。

一种尝试是单独在一行中键入 typedef tree_node

typedef std::unordered_map<std::string, std::pair<std::string, tree_node *>> tree_node;

但是,当它命中声明中的tree_node *时,会给出错误"Expected a type";typedef尚未发生,因此编译器不知道tree_node是什么。 很公平。 我也试图模糊地向前声明tree_node,因为在我看来,当我只通过指针引用它时,编译器不需要有关于它的完整信息:

class tree_node;
typedef std::pair<std::string, tree_node *> tree_value;
typedef std::unordered_map<std::string, tree_value> tree_node;

但这会在最后一行给出错误"使用不同类型的 Typedef 重新定义"。

当然有一种方法可以整理出这罐蠕虫。 如果我可以在tree_nodeunordered_map包裹在struct内时使其工作,为什么当我摆脱了毫无意义的单成员struct时,我不能让它工作? 我基本上只是想让它struct"透明"——我不想在我的代码中继续引用key_val_map。 有办法吗?

如果改为将tree_value声明为结构,则tree_node可以是类型别名。

struct tree_value;
using tree_node = std::unordered_map<std::string, tree_value>;
struct tree_value
{
    std::string data;
    tree_node * child; // or std::unique_ptr<tree_node> ?
};

作为奖励,我们有比firstsecond更有意义的名称。

你可以从地图派生tree_node

struct tree_node : std::unordered_map<std::string, tree_value> {
    using std::unordered_map<std::string, tree_value>::unordered_map;
};