Nehmen wir die “leere” Makrodefinition an
#define FOO
Ist es gültiger Standard C? Wenn ja, was ist FOO
nach dieser Definition?
Nehmen wir die “leere” Makrodefinition an
#define FOO
Ist es gültiger Standard C? Wenn ja, was ist FOO
nach dieser Definition?
Zeta
Es ist einfach ein Makro, das zu nichts erweitert wird. Nun, da das Makro definiert wurde, können Sie es überprüfen #if defined
(oder #ifdef
), ob es definiert wurde.
#define FOO
int main(){
FOO FOO FOO
printf("Hello world");
}
wird erweitern
int main(){
printf("Hello world");
}
Es gibt bestimmte Situationen, in denen dies sehr praktisch ist, zum Beispiel zusätzliche Debug-Informationen, die Sie nicht in Ihrer Release-Version anzeigen möchten:
/* Defined only during debug compilations: */
#define CONFIG_USE_DEBUG_MESSAGES
#ifdef CONFIG_USE_DEBUG_MESSAGES
#define DEBUG_MSG(x) print(x)
#else
#define DEBUG_MSG(x) do {} while(0)
#endif
int main(){
DEBUG_MSG("Entering main");
/* ... */
}
Da das Makro CONFIG_USE_DEBUG_MESSAGES
Wurde definiert, DEBUG_MSG(x)
wird erweitern print(x)
und du wirst bekommen Entering main
. Wenn Sie die entfernen #define
, DEBUG_MSG(x)
erweitert sich zu einem leeren do
–while
Schleife und Sie werden die Nachricht nicht sehen.
Dies ist sehr riskant, da es die Kompilierung beschädigen kann, insbesondere. wenn Sie Aussagen wie haben if (x) DEBUG_MSG("test"); else DEBUG_MSG("test");
. Ich ziehe es vor, mein leeres Makro mit einer wirkungslosen Anweisung wie zu deklarieren #define DEBUG_MSG(x) do {} while(0)
– Eli
24. Februar 2017 um 8:55 Uhr
@Ely Warum sollte das kaputt gehen? Wenn DEBUG_MSG
wurde definiert als #defined DEBUG_MSG(x)
dann else DEBUG_MSG("test")
wird einfach else ;
was gilt, weil ;
ist die “leere Aussage”.
– Pharap
5. Mai 2018 um 23:43 Uhr
Ich mache manchmal so etwas: #define NOTHING
Dann sowas wie int NOTHING main()
– Benutzer12211554
17. Juli 2019 um 21:58 Uhr
@Ely Warum sollte das kaputt gehen? Warum nicht einfach {}
?
– Endolith
27. August 2021 um 18:57 Uhr
Aber in der realen Welt haben Protokollfunktionen verschiedene Parameter DEBUG_MSG("message %s %s %s", parameters, and, more);
. Es ist immer noch kompatibel mit einer solchen Syntax, oder müssen wir aufpassen oder die Parameter, die mit der Funktion im Release-Modus gelöscht werden müssen?
– Sandburg
18. Mai um 8:17 Uhr
md5
Ja, der Standard erlaubt eine leere Definition.
C11 (n1570), § 6.10 Vorverarbeitungsrichtlinien
control-line: # define identifier replacement-list new-line # define identifier lparen identifier-list(opt) ) replacement-list new-line # define identifier lparen ... ) replacement-list new-line # define identifier lparen identifier-list , ... ) replacement-list new-line replacement-list: pp-tokens(opt)
Eine übliche Verwendung sind Inklusionswächter.
#ifndef F_H
# define F_H
#endif
Sie haben nicht beantwortet, was der Wert ist FOO
nach leer definieren.
– Benutzer1150105
15. Dezember 2012 um 12:45 Uhr
@user14284 Makros haben keine Werte. Sie erweitern sich zu einer Liste von Tokens. Diese Liste kann leer sein.
– Melpomen
15. Dezember 2012 um 12:47 Uhr
Leere Makrodefinitionen können auch zur Selbstdokumentation verwendet werden. Das IN
im Code-Snippet unten ist ein Beispiel. Der Code und der Kommentar sind beide aus dem zitiert EDK II-Projekt.
//
// Modifiers for Data Types used to self document code.
// This concept is borrowed for UEFI specification.
//
///
/// Datum is passed to the function.
///
#define IN
typedef
EFI_STATUS
(EFIAPI *EFI_BLOCK_RESET)(
IN EFI_BLOCK_IO_PROTOCOL *This,
IN BOOLEAN ExtendedVerification
);
Ich würde ein anderes Beispiel verwenden. Es muss kein Zitat aus dem tatsächlichen Code sein, aber das aktuelle Beispiel enthält eine ziemlich große Menge unnötiger Informationen. (Stellen Sie übrigens sicher, dass Ihre Antwort immer noch die ursprüngliche Frage beantwortet; sie funktioniert gut mit den anderen Antworten, aber als eigenständige Antwort passt sie nicht wirklich zur Frage “Was tut FOO
erweitern zu”?).
– Zeta
11. August 2015 um 14:14 Uhr
Danke für den Hinweis. Ich lese gerade dieses Stück Code, wenn ich diese Frage sehe. Da die Antwort schon lange ausgewählt wurde, hoffe ich nur, dass meine Antwort als erzieherische Referenz dienen kann.
– smWikipedia
11. August 2015 um 14:48 Uhr
Es ist eine leere Zeichenfolge, und ja, es ist akzeptabel.
– nhahtdh
15. Dezember 2012 um 12:30 Uhr
Nur um darauf hinzuweisen, hier ist eine weitere Frage, die eine interessante Verwendung leerer Definitionen beinhaltet.
– Sidyl
15. Dezember 2012 um 12:40 Uhr