помогите с заголовочными файлами в C - PullRequest
1 голос
/ 24 января 2011

Хорошо, у меня есть довольно хорошее понимание того, как заголовочные файлы должны использоваться в программах на C, но у меня все еще есть эта проблема, которую я, кажется, не могу обойти.Вот ситуация:

Device.c содержит #include "Device.h"

Device.h содержит определение структуры и следующий ...

#ifndef DEVICE_H
#define DEVICE_H
#include "SubDevice.h"
typedef struct {
    subDevice * subDevice1;
    subDevice * subDevice2;
} device;
#endif

SubDevice.c содержит #include SubDevice.h

SubDevice.h содержит определение структуры subDevice и следующее ...

#ifndef SUBDEVICE_H
#define SUBDEVICE_H
#include "Device.h"
typedef struct{
    int MyInt;
    double MyDouble;
}subDevice;
#endif

Проблема заключается в том, что я получаю ошибку компилятора в Device.h вмое определение структуры.В строке subDevice * subDevice1; написано syntax error before subDevice.

Проблема в том, что я включаю заголовочный файл другого файла в каждый файл?Я думал, что операторы #ifndef - #define предотвратят возникновение проблемы ...

Ответы [ 6 ]

4 голосов
/ 24 января 2011

Это не проблема заголовка. Существует проблема на одном typedef, который у вас есть на SubDevice.h. Итак, измените:

typedef struct{
    int MyInt;
    double MyDouble;
}

Кому:

typedef struct{
    int MyInt;
    double MyDouble;
} subDevice;

Ваша проблема должна исчезнуть.

2 голосов
/ 24 января 2011

Проблема в том, что у вас есть круговая ссылка.

Я полагаю, ваш основной файл выглядит примерно так:

#include "Subdevice.h"
#include "Device.h"
int main() {}

Из-за того, как работает препроцессор C (и как вы используете защиту включения), содержимое Device.h будетчитать до Subdevice.h, это означает, что структура subDevice еще не определена при определении структуры device.

Удалите #include "Device.h" из Subdevice.h, и она должна скомпилироваться OK.

2 голосов
/ 24 января 2011

Вы должны поставить точку с запятой после объявления struct, а в вашем typedef отсутствует второй параметр.


РЕДАКТИРОВАТЬ , чтобы отразить редактирование OP

Вы включаете DEVICE_H, который является макросом.

Вам необходимо включить "device.h":

#include "device.h"
1 голос
/ 24 января 2011

Один хороший способ отладки вашего кода с ошибками препроцессора - gcc -E <files>, так что вы действительно можете увидеть, как будет выглядеть ваша программа после того, как этот препроцессор покончит с ней.

1 голос
/ 24 января 2011

То, что вам, по-видимому, не хватает, - это хорошее понимание модели компиляции, используемой компиляторами C (и C ++).
Компиляция исходного файла на C или C ++ может быть разделена на три этапа:

  1. Препроцессирование
  2. 1007 * Компиляция *
  3. Linking

1012 * Препроцессирование * Во время предварительной обработки компилятор (или отдельный препроцессор) просматривает исходный файл и выполняет расширение макроса и #include замены.
Все директивы #include заменяются содержимым ссылочного файла. Все определения макросов обрабатываются, и там, где в тексте происходит вызов макроса, он заменяется текстом замены. Это полностью текстовый процесс. После предварительной обработки в исходном коде не осталось директив препроцессора (строки, начинающиеся с #) 1022 * Компиляция * Во время компиляции компилятор интерпретирует исходный код в соответствии с правилами языка C (или C ++) и переводит код в объектный код. Linking

На этапе компоновки все объектные файлы объединяются вместе и связываются с соответствующими библиотеками для создания исполняемого файла.


Исходный код, представленный здесь, имеет две проблемы:

  1. Файл subdevice.h содержит ложную директиву #include DEVICE_H. Об этом должен сообщить препроцессор / компилятор, поскольку DEVICE_H не разрешает имя файла в кавычках или угловых скобках.
  2. Отсутствует точка с запятой (;) (и отсутствует имя typedef) в конце typedef в subdevice.h. В результате компилятор пытается объединить это со следующими строками кода (typedef struct в device.h) и ужасно запутывается. Это вызывает сообщение об ошибке синтаксиса.
1 голос
/ 24 января 2011

У вас есть "typedef struct {...}" в вашем subdevice.h, когда вы должны иметь "typedef struct {...} subDevice;"

Строка "#include DEVICE_H" также выглядитнесколько неправильно.Вы имели в виду #include "device.h"?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...