Wenn ich eine source.c-Datei mit einer Struktur habe:
struct a {
int i;
struct b {
int j;
}
};
Wie kann diese Struktur in einer anderen Datei (dh func.c
) verwendet werden?
Soll ich eine neue Header-Datei erstellen, die Struktur dort deklarieren und diesen Header einfügen func.c
?
Oder sollte ich die gesamte Struktur in einer Header-Datei definieren und diese in beide source.c
und aufnehmen func.c
? Wie kann die Struktur extern
in beiden Dateien deklariert werden?
Soll ich typedef
es? Wenn das so ist, wie?
struct b
, aber danna
deklariert Ihre Struktur einen Typ, der nicht verwendet wird (Sie sollten wahrscheinlich einen Mitgliedsnamen definieren, möglicherweisek
nach der inneren engen Klammer und vor dem Semikolon.Antworten:
Wenn diese Struktur von einer anderen Datei func.c verwendet werden soll, wie geht das?
Wenn ein Typ in einer Datei verwendet wird (dh eine func.c-Datei), muss er sichtbar sein. Der schlechteste Weg, dies zu tun, ist das Kopieren und Einfügen in jede benötigte Quelldatei.
Der richtige Weg ist, es in eine Header-Datei einzufügen und diese Header-Datei bei Bedarf einzuschließen.
Sollen wir eine neue Header-Datei öffnen und die Struktur dort deklarieren und diesen Header in die func.c aufnehmen?
Dies ist die Lösung, die mir besser gefällt, weil sie den Code sehr modular macht. Ich würde Ihre Struktur wie folgt codieren:
Ich würde Funktionen, die diese Struktur verwenden, in denselben Header einfügen (die Funktion, die "semantisch" Teil ihrer "Schnittstelle" ist).
Und normalerweise könnte ich die Datei nach dem Strukturnamen benennen und diesen Namen erneut verwenden, um die definierten Header-Guards auszuwählen.
Wenn Sie eine Funktion mit einem Zeiger auf die Struktur deklarieren müssen, benötigen Sie nicht die vollständige Strukturdefinition. Eine einfache Vorwärtserklärung wie:
Wird ausreichen, und es verringert die Kopplung.
oder können wir die Gesamtstruktur in der Header-Datei definieren und diese sowohl in source.c als auch in func.c aufnehmen?
Dies ist ein anderer Weg, der etwas einfacher, aber weniger modular ist: Einige Codes, für deren Funktion nur Ihre Struktur erforderlich ist, müssen noch alle Typen enthalten.
In C ++ könnte dies zu interessanten Komplikationen führen, aber dies ist nicht zum Thema (kein C ++ - Tag), daher werde ich nicht näher darauf eingehen.
dann, wie diese Struktur in beiden Dateien als extern deklariert wird. ?
Ich verstehe den Punkt vielleicht nicht, aber Greg Hewgill hat eine sehr gute Antwort in seinem Beitrag. Wie deklariere ich eine Struktur in einem Header, die von mehreren Dateien in c verwendet werden soll? .
sollen wir es dann wie tippen?
Der Grund dafür ist, dass die Verwaltung von C-Strukturen schmerzhaft sein kann: Sie müssen das Schlüsselwort struct überall dort deklarieren, wo es verwendet wird:
Mit einem typedef können Sie es ohne das Schlüsselwort struct schreiben.
Es ist wichtig, dass Sie immer noch einen Namen für die Struktur behalten. Schreiben:
erstellt nur eine anonyme Struktur mit einem typisierten Namen, und Sie können sie nicht weiter deklarieren. Halten Sie sich also an das folgende Format:
Auf diese Weise können Sie MyStruct überall dort verwenden, wo Sie das Hinzufügen des Schlüsselworts struct vermeiden möchten, und MyStructTag weiterhin verwenden, wenn ein typedef nicht funktioniert (dh eine Vorwärtsdeklaration).
Bearbeiten:
Die falsche Annahme bezüglich der C99-Strukturdeklaration wurde korrigiert, wie Jonathan Leffler zu Recht bemerkte .
Bearbeiten 2018-06-01:
Craig Barnes erinnert uns in seinem Kommentar daran, dass Sie aus Gründen der Klarheit keine separaten Namen für den Strukturnamen "tag" und den Namen "typedef" verwenden müssen, wie ich es oben getan habe.
In der Tat könnte der obige Code gut geschrieben werden als:
IIRC, genau das macht C ++ mit seiner einfacheren Strukturdeklaration hinter den Kulissen, um die Kompatibilität mit C zu gewährleisten:
Zurück zu C habe ich beide Verwendungen gesehen (separate Namen und gleiche Namen), und keine hat mir bekannte Nachteile. Die Verwendung desselben Namens vereinfacht das Lesen, wenn Sie keine separaten C-Namespaces für Strukturen und andere Symbole verwenden .
quelle
struct
Tag und dentypedef
Namen zu verwenden. C verwendet einen anderen Namespace fürstruct
Tags, sodass SieMyStruct
beide verwenden können.Für eine Strukturdefinition, die für mehr als eine Quelldatei verwendet werden soll, sollten Sie sie definitiv in eine Header-Datei einfügen. Fügen Sie diese Header-Datei dann in jede Quelldatei ein, die die Struktur benötigt.
Die
extern
Deklaration wird nicht für Strukturdefinitionen verwendet, sondern für Variablendeklarationen (dh einige Datenwerte mit einem von Ihnen definierten Strukturtyp). Wenn Sie dieselbe Variable für mehr als eine Quelldatei verwenden möchten, deklarieren Sie sie wieextern
in einer Header-Datei wie:Definieren Sie dann in einer Quelldatei die tatsächliche Variable:
Wenn Sie dies vergessen oder versehentlich in zwei Quelldateien definieren, informiert Sie der Linker darüber.
quelle
GLOBAL
alsextern
oder nichts oben im Header zu definieren und dann Variablen als zu deklarierenGLOBAL struct a myAValue;
. In den meisten Quelldateien legen Sie fest, dass die#define GLOBAL extern
Version verwendet wird ( Deklarieren der Variablen), und in genau einer Quelldatei wird die leere Definition verwendet, sodass die Variablen definiert werden .Ah:
Jetzt müssen Sie nur noch ah in die Dateien aufnehmen, in denen Sie diese Struktur verwenden möchten.
quelle