0

我是 C 编程新手,并且有以下代码。我面临以下错误。

typedef struct Vertex Vertex;
typedef struct Edge Edge;

struct Vertex {
   bool known;
   char id[25];
   Edge edges[20];
   int distance;
};

struct Edge {
   Vertex target;
   int weight;
};

typedef struct {
   Vertex Nodes[20];
   int pass;
   int infinity;
} Graph;

它给出的错误是:

数组类型具有不完整的元素类型

有人可以帮我理解问题所在吗?

4

5 回答 5

1
typedef struct Vertex Vertex;
typedef struct Edge Vertex;

这可能会产生一些名称冲突,只需更改其中一个的名称即可。

于 2013-09-21T21:40:44.310 回答
0

唯一可行的方法是混合使用指针并解决如何实现VertexEdge结构:

/*your typedefs didn't make sense to me as it was conflicting. So, I edited it accordingly*/
//typedef struct Vertex Vertex;
//typedef struct Edge Vertex;

struct Vertex;
struct Edge;

typedef struct Vertex {
   bool known;
   char id[25];
   struct Edge *edges;//This HAS to be a pointer.
   int distance;
} Vertex;

typedef struct Edge {
   Vertex target;
   int weight;
} Edge;

typedef struct {
   Vertex Nodes[20];
   int pass;
   int infinity;
} Graph;

为什么这行得通?由于称为前向声明的东西:

...前向声明是程序员尚未给出完整定义的标识符(表示实体,如类型、变量或函数)的声明。编译器需要知道标识符的类型(内存分配的大小,类型检查的类型,例如函数的签名),但不需要知道它所持有的特定值(如果是变量)或定义(如果是函数)...

于 2013-09-21T21:43:51.293 回答
0

想一想:编译器必须知道 Vertex 和 Edge 结构的大小。如果你让 Edge 包含一个 Vertex 并且 Vertex 包含一个 Edge ,它并不能真正理清大小。解决方案是只提供一个指向结构的指针(编译器应该知道指针大小)。我会使用 jrd1 版本,稍作改动:

struct Edge {
   struct Vertex* target;
   int weight;
} Edge;

typedef struct Vertex {
   bool known;
   char id[25];
   struct Edge edges[20];
   int distance;
} Vertex;

typedef struct {
   Vertex Nodes[20];
   int pass;
   int infinity;
} Graph;

那应该工作得很好。

此外,如果每条边都应该指向包含它的顶点,那么您实际上不需要存储该指针,如果需要,您可以使用linux 内核中的container_of宏之类的东西。

于 2014-03-26T14:31:33.267 回答
0

有人可以帮我理解问题所在吗?

数组具有以下属性:

  1. 它的所有元素都具有相同的大小。
  2. 元素是连续存储的。

id[i]这允许根据第一个元素的大小和内存地址以及索引来计算每个元素的内存地址(例如) i

为此,编译器需要知道数组元素有多大。当您声明该Vertex::edges[20]成员时,编译器还不知道该类型的对象有多大Edge。因此编译器错误。

避免这种情况的一种方法是在Edge结构之前定义Vertex结构。在您的情况下,这将无济于事,因为Edge::targetis 类型Vertex并且您会收到类似的错误。结构成员的内存地址是使用对象的内存地址并加上请求成员之前的成员的大小(可能还有一些填充)来计算的。

在这种具有循环依赖关系的情况下,可以使用指针作为成员,因为指向结构的指针与指针指向的结构具有相同的大小,无论结构具有哪些成员。

于 2013-09-21T22:27:41.030 回答
0

在这份声明中

struct Vertex {
   bool known;
   char id[25];
   Edge edges[20];
   int distance;
};

该类型Edge尚未声明。这里的编译器只知道它将对应于 a struct Edge,但它struct本身是未知的。

于 2013-09-21T22:32:14.903 回答