Kompilacja warunkowa
ifdef i makra
Kompilacja warunkowa to bezpłatna lekcja C Academy na CoddyKit. To lekcja 1 z 4. Możesz przeczytać całą lekcję poniżej za darmo — a potem ćwiczyć ją interaktywnie w przeglądarce z wbudowanym edytorem kodu i tutorem AI dostępnym 24/7. To część ścieżki edukacyjnej C Academy, a Twój postęp synchronizuje się między webem a aplikacją CoddyKit. Kurs C Academy zawiera 4 lekcji w sumie.
Preprocesor
Zanim kompilator w ogóle zobaczy kod, uruchamiany jest preprocesor. Obsługuje on każdy wiersz zaczynający się od #: dołączanie plików, makra i instrukcje warunkowe.
Kompilacja warunkowa pozwala dołączać lub wykluczać bloki kodu na podstawie warunków ocenianych na tym etapie, dzięki czemu z jednego źródła można tworzyć różne kompilacje.
Definiowanie makr
#define tworzy makro. Bez wartości jest ono po prostu flagą, którą można później sprawdzać.
Makra obiektowe zastępują nazwę tekstem, natomiast flagi jedynie oznaczają, że coś zostało ustawione.
#define MAX_USERS 100 /* value macro */
#define DEBUG /* flag macro */ifdef i ifndef
#ifdef NAME pozostawia blok tylko wtedy, gdy NAME jest zdefiniowane. #ifndef pozostawia go tylko wtedy, gdy NAME nie jest zdefiniowane.
W tym przypadku komunikat debugowania istnieje tylko w kompilacjach debugowych. Jeśli DEBUG nie jest zdefiniowane, kompilator w ogóle nie zobaczy tego wiersza.
#include <stdio.h>
#define DEBUG
int main(void) {
#ifdef DEBUG
printf("debug: starting\n");
#endif
printf("running\n");
return 0;
}if, elif, else
#if oblicza stałe wyrażenie całkowitoliczbowe. W połączeniu z #elif i #else umożliwia wybór jednej z wielu możliwości.
W ten sposób kod jest wybierany na podstawie makra zawierającego numer wersji.
#include <stdio.h>
#define VERSION 2
int main(void) {
#if VERSION >= 2
printf("new feature on\n");
#else
printf("legacy mode\n");
#endif
return 0;
}Operator defined
Wewnątrz #if można sprawdzić, czy coś jest zdefiniowane, za pomocą defined(NAME), a testy łączyć operatorami && i ||.
Jest to bardziej elastyczne niż #ifdef, które może sprawdzać tylko jedną nazwę.
#if defined(LINUX) && !defined(EMBEDDED)
/* desktop Linux code */
#endifDefiniowanie podczas kompilacji
Nie trzeba wpisywać makr na stałe w kodzie. Flaga -D definiuje je w wierszu poleceń.
W ten sposób systemy budowania przełączają funkcje bez edytowania kodu źródłowego. -DDEBUG działa tak samo jak #define DEBUG na początku każdego pliku.
gcc -DDEBUG -DVERSION=3 -o app app.cWykrywanie platformy
Kompilatory wstępnie definiują makra opisujące platformę docelową. Można ich używać do pisania przenośnego kodu.
_WIN32— Windows (32- lub 64-bitowy)__linux__— Linux__APPLE__— macOS / iOS
Na ich podstawie należy wybierać wywołania odpowiedniego API platformy.
#ifdef _WIN32
#include <windows.h>
#else
#include <unistd.h>
#endifStrażniki dołączania nagłówków
Klasycznym zastosowaniem instrukcji warunkowych jest strażnik dołączania, który zapobiega dwukrotnemu przetworzeniu pliku nagłówkowego.
Pierwsze dołączenie definiuje makro strażnika; kolejne pomijają zawartość, ponieważ makro jest już zdefiniowane.
#ifndef UTILS_H
#define UTILS_H
int add(int a, int b);
#endif /* UTILS_H */Wyłączanie fragmentu kodu komentarzem
#if 0 ... #endif niezawodnie wyłącza blok, nawet jeśli zawiera on już komentarze.
W przeciwieństwie do /* */ można go bezpiecznie zagnieżdżać, dlatego jest standardowym sposobem tymczasowego wykluczania kodu podczas debugowania.
#if 0
legacy_function(); /* disabled for now */
/* with internal comments too */
#endifSprawdzanie wyniku preprocesora
Aby dokładnie zobaczyć, co skompiluje kompilator, należy uruchomić tylko preprocesor za pomocą -E.
Rozwija on wszystkie dołączenia, makra i instrukcje warunkowe, co jest niezwykle pomocne, gdy makro działa nieprawidłowo.
gcc -E app.c | lessPrzełączniki funkcji w praktyce
Często stosowanym wzorcem jest pojedynczy nagłówek konfiguracyjny, który włącza lub wyłącza funkcje w całym projekcie.
Wystarczy zmienić jedno #define, aby każdy chroniony blok we wszystkich plikach zareagował. Dzięki temu opcjonalne funkcje są wyraźnie oddzielone od podstawowego kodu.
#include <stdio.h>
#define FEATURE_LOGGING 1
int main(void) {
#if FEATURE_LOGGING
printf("logging enabled\n");
#endif
printf("app ready\n");
return 0;
}Szybkie sprawdzenie
Proszę przewidzieć działanie definicji przekazanej w wierszu poleceń.
Podsumowanie
Potrafi już Pan/Pani kontrolować kompilację warunkową:
#ifdef/#ifndefsprawdzają, czy makro jest zdefiniowane#if/#elif/#elseobliczają stałe wyrażenia, wraz zdefined()-DNAMEdefiniuje makra w wierszu poleceń, umożliwiając przełączanie funkcji- Wstępnie zdefiniowane makra platformy ułatwiają pisanie przenośnego kodu, a strażniki dołączania zapobiegają wielokrotnemu dołączaniu plików
Następnie: organizowanie kodu w wielu plikach.
Często zadawane pytania
Czy lekcja „Kompilacja warunkowa” jest bezpłatna?
Tak — pełny tekst „Kompilacja warunkowa” jest dostępny za darmo tutaj w sieci. Aby ćwiczyć ją interaktywnie (wbudowany edytor kodu i tutor AI dostępny 24/7) i odblokować resztę kursu C Academy, przejdź na CoddyKit PRO. Kurs C Academy zawiera 4 lekcji w sumie.
Co nauczysz się w „Kompilacja warunkowa”?
ifdef i makra Ćwiczysz C Academy z praktycznym kodem, który uruchamiasz bezpośrednio w przeglądarce, a tutor AI dostępny 24/7 odpowiada na Twoje pytania podczas pracy nad lekcją.
Czy potrzebuję doświadczenia, aby zacząć C Academy?
Nie wymagamy żadnego doświadczenia. C Academy w CoddyKit jest strukturyzowany dla początkujących i zaawansowanych użytkowników, więc możesz zacząć tutaj lub od początku i uczyć się w swoim tempie. To lekcja 1 z 4.
Ile czasu zajmuje lekcja „Kompilacja warunkowa”?
Większość lekcji CoddyKit trwa około 5–10 minut. Każda lekcja to mały, interaktywny krok, dzięki czemu robisz systematyczne postępy i zawsze wracasz dokładnie do tego samego miejsca — na webie i w aplikacji.
Czy mogę pisać i uruchamiać kod w tej lekcji C Academy?
Tak. Każda lekcja C Academy zawiera wbudowany edytor kodu, więc piszesz i uruchamiasz prawdziwy kod bezpośrednio w przeglądarce i od razu otrzymujesz sprzężenie zwrotne od AI — bez konfiguracji na komputerze.
Wszystkie lekcje w tym kursie
- Kompilacja warunkowa
- Projekty wieloplikowe
- Makefile
- Biblioteki statyczne i współdzielone