2016-12-03 4 views
1

Я видел вопросы о структурах, которые имеют указатели друг на друга, я много пробовал, но я просто не могу решить свою проблему. Мой мозг просто горит!Структуры, ссылающиеся друг на друга

У меня есть две различные структуры/типы: set_t и node_t

#ifndef _SETH_ 
#define _SETH_  
#include "node.h" 
#include "list.h" 

typedef struct { 
    list_t* list; 

}set_t; 

set_t* createSet(node_t*); 
set_t* findSet(node_t*); 
set_t* unionSet(node_t*, node_t*); 

#endif 

не имеют никакого node_t в моей структуре set_t, но я использую node_t в качестве параметров, поэтому я включаю node.h, как вы можете видеть. Список - это связанный список узлов, но пока это не связано с моей проблемой.

#ifndef _NODEH_  
#define _NODEH_ 

//?? #include "set.h" 
typedef struct set_t s; 

typedef struct node_t{ 
    int color; 
    int dist; 
    int key; 
    int date; 
    int end; 
    s* set; 
    struct node_t* father; 
}node_t; 

node_t* createNode(int); 
#endif 

В самом начало, я использую, чтобы включить set.h в node.h, потому что я использую набор в моей узловой структуре. Но у меня был какой-то «цикл» с включенными. Так I'im пытается использовать эту инструкцию:

typedef struct set_t s; 

таким образом, чтобы избежать зацикливания проблемы.

Но на этот раз у меня есть другая проблема/предупреждение, что я думаю, что я понимаю: , когда я делаю что-то вроде (давайте предположим, что мы имеем node_t * п):

set_t* s = (set_t*)malloc(sizeof(set_t)); 
    n->set= s; 

У меня есть присваивание от несовместимого предупреждение указателя типа, возможно, потому что s является set_t *, но n-> установлено как * ...

Что я делаю неправильно? Я действительно хочу понять, как это работает, когда вы хотите включить xh в yh и yh в xh ... То же самое, если yh нуждается в xh, zh нуждается в yh, а xh нуждается в zh .. Я очень надеюсь, что я достаточно ясен для вас, ребята, чтобы помочь мне.

+3

http://stackoverflow.com/questions/888386/resolve-circular-typedef-dependency. не нажимайте malloc return. 'void *' выполняет эту работу. не печатайте структуру дважды. делайте это только в одном заголовке. – Stargateur

ответ

1

Компилятор принимает тип s как нечто иное, чем тип set_t.

Для выравнивания этого выполните следующие действия:

В set.h изменения

typedef struct { 
    list_t * list; 
} set_t; 

быть

typedef struct Set { 
    list_t* list; 
} set_t; 

В node.h изменения

typedef struct set_t s; 

быть

typedef struct Set set_t; // True forward declaration of set_t. 

и

s * set; 

быть

set_t * set; 

Обновление:

Бросив все те бесполезно typedef возможно делает вещи яснее. Ваш код будет выглядеть следующим образом:

комплект.ч

#ifndef _SETH_ 
#define _SETH_ 

#include "node.h" 
#include "list.h" 

// define type "struct Set" 
struct Set { 
    struct List * list; // defintion of struct List to be adjusted in list.h 
}; 

struct Set * createSet(struct Node*); 
struct Set * findSet(struct Node*); 
struct Set * unionSet(struct Node*, struct Node*); 


#endif 

node.h

#ifndef _NODEH_  
#define _NODEH_ 

// declare forward type "struct Set" 
struct Set; 

// define type "struct Node" 
struct Node { 
    int color; 
    int dist; 
    int key; 
    int date; 
    int end; 
    struct Set * set; 
    struct Node* father; 
}; 

struct Node * createNode(int); 


#endif 
+0

Большое спасибо за ваше время, у меня есть еще один вопрос, если у вас есть больше времени для меня, что мы делаем точно? Переименовываем ли мы структуру или что-то еще? Когда мы делаем typedef struct Set { list_t * list; } set_t; Что такое «Установить»? и что такое «set_t»? –

+1

'struct Set' - это тип данных типа * named * struct. Используя 'typedef', вы просто создаете другой тип в другом пространстве имен для одной и той же вещи. На самом деле вы усложняете вещи, и, как обычно, когда усложняющие вещи увеличивают вероятность недоразумений, с которыми вы столкнулись. @MonsieurOurer – alk

+0

ОК, теперь это яснее, спасибо вам большое за вашу помощь :) –