Как декларация может конфликтовать с самим собой? - PullRequest
7 голосов
/ 24 августа 2010

Это ошибка, которую я получаю, когда пытаюсь скомпилировать код, который использует тауки (не мой код):

.../taucs/src/taucs.h:554: error: conflicting declaration ‘typedef struct taucs_ccs_matrix taucs_ccs_matrix’
.../taucs/src/taucs.h:554: error: ‘taucs_ccs_matrix’ has a previous declaration as ‘typedef struct taucs_ccs_matrix taucs_ccs_matrix’

ват?Это противоречит самому себе?

После того, как я ущипнул себя, я создал тестовый заголовок и вставил противоречивое определение, просто чтобы убедиться, что я был прав:

В файле testit.h:

#include "somethingelse.h"

typedef struct
{
  int n;
} foobar;

В файле someelse.h:

typedef struct
{
  int n;
} foobar;

Конечно, я получаю:

testit.h:6: error: conflicting declaration ‘typedef struct foobar foobar’
somethingelse.h:4: error: ‘foobar’ has a previous declaration as ‘typedef struct foobar foobar’

Или, если у меня есть это в testit.h:

typedef struct
{
  int n;
} foobar;

typedef struct
{
  int n;
} foobar;

testit.h:9: error: conflicting declaration ‘typedef struct foobar foobar’
testit.h:4: error: ‘foobar’ has a previous declaration as ‘typedef struct foobar foobar’

Номер строки всегда отличается - объявление не может конфликтовать с самим собой.Я не понимаюКто-нибудь когда-нибудь видел это?

Ответы [ 5 ]

14 голосов
/ 24 августа 2010

Включен ли один заголовок в несколько исходных файлов? Если это так, вам нужно обернуть его в «включить охрану» следующим образом:

#ifndef TAUCS_H
#define TAUCS_H

//Header stuff here

#endif //TAUCS_H
6 голосов
/ 24 августа 2010

Может ли быть так, что ваш заголовочный файл (.../taucs/src/taucs.h), который содержит объявление, (прямо или косвенно) включен дважды с помощью двух отдельных директив #include?

1 голос
/ 24 августа 2010
typedef struct
{
   int n;
} foobar;

typedef struct
{
   int n;
} foobar;

testit.h:9: error: conflicting declaration ‘typedef struct foobar foobar’
testit.h:4: error: ‘foobar’ has a previous declaration as ‘typedef struct foobar foobar’

В этом примере вы даете 2 объявления foobar.Компилятор не знает, какой из них выбрать, поэтому он выручает с конфликтующим объявлением.Вы не можете объявить одно и то же дважды.

0 голосов
/ 17 мая 2016

У меня была та же проблема, связанная с моим кодом, и это было не двойное объявление типа. PC-Lint жаловался на тот же typedef, который используется в смешанном коде на C и C ++. Я мог бы исправить это, избегая того же объявления в файлах C и C ++. Надеюсь, это кому-нибудь поможет.

0 голосов
/ 24 августа 2010

Не повторяйте определение. C ++ позволяет определению появляться только один раз. Что вы можете сделать, это повторить декларацию.

A typedef - это всегда определение. Поэтому первое, что я бы порекомендовал, это дать собственному struct имя (и поскольку это C ++, typedef не добавляет никаких преимуществ, поэтому просто отбросьте typedef):

// file1.h
struct foobar
{
    int n;
};

Далее, это должно быть ровно в одном файле. Если у вас есть файлы, которые используют только указатели на foobar, вы можете повторить объявление (только не определение):

// file2.h

// This is just a declaration so this can appear as many times as
// you want
struct foobar;

void doit(const foobar *f); 
...