Historisch wurde Modularität als ein Weg entwickelt, große Projekte in unabhängige logische Teile zu unterteilen, um die Lesbarkeit, Wiederverwendbarkeit von Code und die Verteilung von Verantwortung zwischen Entwicklern zu verbessern. In C wird Modularität auf Dateiebene realisiert — Quell- (.c) und Header-Dateien (.h).
Ein Problem, mit dem Programmierer konfrontiert sind: Wie kann man die Interaktion zwischen den Code-Teilen organisieren, Duplikation von Definitionen vermeiden, die Kapselung nicht verletzen und das Bauen vereinfachen?
Lösungen sind die Trennung von Schnittstelle und Implementierung:
Beispiel einer modularen Code-Struktur:
// mymath.h #ifndef MYMATH_H #define MYMATH_H int add(int, int); #endif // mymath.c #include "mymath.h" int add(int a, int b) { return a + b; } // main.c #include "mymath.h" #include <stdio.h> int main() { printf("%d ", add(3, 4)); return 0; }
Schlüsselfunktionen:
Kann man eine Variable mit extern in einer Header-Datei definieren und sicher in mehreren Modulen verwenden?
Nein! Globale Variablen sollten nur in einer .c-Datei definiert und in Header-Dateien nur über extern deklariert werden. Andernfalls treten Linker-Fehler aufgrund von „multiple definition“ auf.
Muss jede Header-Datei durch #include nur einmal eingebunden werden?
Es ist notwendig, jede .h-Datei durch Wachmakros (#ifndef/#define/#endif) zu umschließen, andernfalls treten bei mehreren Einfügungen Namenskonflikte und Kompilierungsfehler auf.
Kann man in C reine Kapselung privater Daten einer Struktur (opaque pointer) implementieren?
Ja. Der sogenannte „opaque pointer“ ermöglicht es, die Details einer Struktur vor dem Benutzer zu verbergen:
// mystruct.h typedef struct MyStruct MyStruct; MyStruct* create(void); void destroy(MyStruct*); // mystruct.c struct MyStruct { int a; };
Die gesamte Logik ist in einer langen .c-Datei implementiert, der Code wiederholt sich, globale Variablen überschneiden sich, es treten Linker-Fehler auf.
Vorteile:
Nachteile:
Der Code ist modularisiert, Include Guards werden verwendet, private Daten sind durch opaque pointer verborgen.
Vorteile:
Nachteile: