结构体 X 中嵌套结构体 X?

6
这可能非常简单,但是在C语言中如何使结构体“x”成为结构体“x”?例如:
typedef struct _Node {
    Node node;
} Node;

我做了一些研究并尝试使用指针,像这样:

typedef struct _Node {
    struct Node *node;
} Node;

尽管这样会将变量节点留下作为一个指针,但我不想要它,我只想让它成为Node结构的实例。感谢您的帮助。 :)
编辑:
本质上,我试图做的是:
Node current = createNode(...);
while (true) {
    Node node = createNode(..., &current);
    addToList(node);
    current = somethingElse();
}

您可能想象得到,我希望一个普通节点进入createNode()函数:

Node createNode(..., Node node) {}

14
你不能那样做。要理解递归,你必须先理解递归。 - DCoder
@DCoder 那么什么是理想的解决方法? - Mr Cherno
4
使用指针,就像你在研究中发现的那样。 - Tomer Arazy
5
如果类型为 Node 的变量包含一个名为 node、类型为 Node 的成员变量,那么该成员变量中也包含一个名为 node、类型为 Node 的成员变量……它们会形成一个无限的链。由于没有其他内容,你只能沿着这个无限链进行操作,却永远无法到达终点。 - user2404501
如果我使用指针,那么它不是使用变量的实例而是使用副本吗?所以如果我改变它所指向的变量,指针也会改变吗?我该如何解决这个问题? - Mr Cherno
显示剩余6条评论
2个回答

8
typedef struct node {
    struct node node;
} node_s;

这将导致“无限递归”。换句话说,它的大小将是无限的。编译器无法回答这个问题:分配多少内存?因此,它会抛出一个诊断消息。
这就是为什么您必须使用指针来创建自引用类型的原因。
typedef struct node {
    struct node *node;
} node_s;

顺便提一句,以两个下划线或大写字母开头的标识符是留给实现部分使用的。


3
那是不可能的。因为它属于不完整类型。没有 struct Nodestruct Node 里面再加上 struct Node ...... 依此类推...... 这就使你原来的结构不完整。因此是不完整的类型定义。
原因是:
  1. 为了将字段放入一个结构体中,它必须是已知类型。
  2. 但是在看到 struct Node{} 中的 struct Node 时,还不能确定。
  3. 只有扫描所有关于 struct Node{} 的定义之后才能确定,但这只有在知道 struct Node 的类型后才可能出现,这导致了一个 悖论
但是如果包含 struct Node *,情况就不同了。
  1. 当到达 struct Node * 时,您知道它是指针类型。无论指针的类型如何,它都需要固定量的存储空间。
  2. 因此,它成功地扫描并完成了 struct Node{} 的定义。因此它是一个完整的类型。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接