Implementation defined behavior control
Implementation defined behavior wird gesteuert durch die #pragma Direktive.
Inhaltsverzeichnis |
Syntax
#pragma
pragma-params
|
(1) | ||||||||
_Pragma(
string-literal
)
|
(2) | (seit C++11) | |||||||
L
-Präfix (falls vorhanden), die äußeren Anführungszeichen und führende/abschließende Leerzeichen von
string-literal
, ersetzt jedes
\
"
durch
"
und jedes
\\
durch
\
, tokenisiert dann das Ergebnis (wie in
Übersetzungsphase 3
) und verwendet das Ergebnis dann als wäre es die Eingabe für
#pragma
in
(1)
.
Erklärung
Die Pragma-Direktive steuert implementierungsspezifisches Verhalten des Compilers, wie das Deaktivieren von Compiler-Warnungen oder das Ändern von Ausrichtungsanforderungen. Jedes nicht erkannte Pragma wird ignoriert.
Nicht standardkonforme Pragmas
Der ISO C++-Sprachstandard verlangt nicht, dass Compiler irgendwelche Pragma-Anweisungen unterstützen. Allerdings werden mehrere nicht-standardisierte Pragmas von verschiedenen Implementierungen unterstützt:
#pragma STDC
Der ISO-C-Sprachstandard verlangt, dass C-Compiler die folgenden drei Pragmas unterstützen, und einige C++-Compilerhersteller unterstützen diese in unterschiedlichem Maße in ihren C++-Frontends:
#pragma STDC FENV_ACCESS
arg
|
(1) | ||||||||
#pragma STDC FP_CONTRACT
arg
|
(2) | ||||||||
#pragma STDC CX_LIMITED_RANGE
arg
|
(3) | ||||||||
wobei
arg
entweder
ON
,
OFF
oder
DEFAULT
ist.
ON
gesetzt, informiert dies den Compiler, dass das Programm auf die
Gleitkommaumgebung
zugreifen oder sie ändern wird, was bedeutet, dass Optimierungen, die Flag-Tests und Modusänderungen untergraben könnten (z.B. globale Common Subexpression Elimination, Code Motion und Constant Folding), untersagt sind. Der Standardwert ist implementierungsdefiniert, in der Regel
OFF
.
ON
.
+v 2
) , und |x+iy| = √ x 2
+y 2
, trotz der Möglichkeit von Zwischenüberläufen. Mit anderen Worten garantiert der Programmierer, dass der Wertebereich der an diese Funktionen übergebenen Werte begrenzt ist. Der Standardwert ist
OFF
.
Das Verhalten des Programms ist undefiniert, falls eine der drei oben genannten Pragmas in einem anderen Kontext als außerhalb aller externen Deklarationen oder vor allen expliziten Deklarationen und Anweisungen innerhalb eines zusammengesetzten Anweisungsblocks erscheint.
Hinweis: Compiler, die diese Pragmas nicht unterstützen, können äquivalente Kompilierzeitoptionen bereitstellen, wie z.B. gccs
-fcx-limited-range
und
-ffp-contract
.
#pragma once
#pragma once ist ein nicht-standardisiertes Pragma, das von der überwiegenden Mehrheit moderner Compiler unterstützt wird. Wenn es in einer Header-Datei erscheint, zeigt es an, dass sie nur einmal geparst werden soll, selbst wenn sie (direkt oder indirekt) mehrmals in derselben Quelldatei eingebunden wird.
Standardmethode zur Vermeidung mehrfacher Einbindung derselben Header-Datei ist die Verwendung von Include Guards :
#ifndef LIBRARY_FILENAME_H #define LIBRARY_FILENAME_H // Inhalt der Header-Datei #endif /* LIBRARY_FILENAME_H */
Damit alle bis auf die erste Einbindung der Header-Datei in jeder Übersetzungseinheit von der Kompilierung ausgeschlossen werden. Alle modernen Compiler merken sich, dass eine Header-Datei einen Include-Guard verwendet und parsen die Datei nicht erneut, wenn sie erneut auftaucht, solange der Guard noch definiert ist (siehe z.B. gcc ).
Mit #pragma once erscheint derselbe Header als
#pragma once // Inhalt der Header-Datei
Im Gegensatz zu Header-Guards macht dieses Pragma es unmöglich, fälschlicherweise denselben Makronamen in mehr als einer Datei zu verwenden. Andererseits, da mit #pragma once Dateien basierend auf ihrer Dateisystem-Identität ausgeschlossen werden, kann dies nicht davor schützen, einen Header zweimal einzubinden, wenn er an mehr als einer Stelle in einem Projekt existiert.
#pragma pack
Diese Familie von Pragmas steuert die maximale Ausrichtung für anschließend definierte Klassen- und Union-Mitglieder.
#pragma pack(
arg
)
|
(1) | ||||||||
#pragma pack()
|
(2) | ||||||||
#pragma pack(push)
|
(3) | ||||||||
#pragma pack(push,
arg
)
|
(4) | ||||||||
#pragma pack(pop)
|
(5) | ||||||||
wobei arg eine kleine Zweierpotenz ist und die neue Ausrichtung in Bytes angibt.
#pragma pack kann die Ausrichtung einer Klasse verringern, jedoch kann es eine Klasse nicht überausrichten.
Siehe auch spezifische Details für GCC und MSVC .
|
Dieser Abschnitt ist unvollständig
Grund: Erklären Sie die Auswirkungen dieser Pragmas auf Datenmember sowie die Vor- und Nachteile ihrer Verwendung. Quellen als Referenz: |
|
Dieser Abschnitt ist unvollständig
Grund: Kein Beispiel |
Referenzen
- C++23-Standard (ISO/IEC 14882:2024):
-
- 15.9 Pragma-Direktive [cpp.pragma]
- C++20-Standard (ISO/IEC 14882:2020):
-
- 15.9 Pragma-Direktive [cpp.pragma]
- C++17-Standard (ISO/IEC 14882:2017):
-
- 19.6 Pragma-Direktive [cpp.pragma]
- C++14-Standard (ISO/IEC 14882:2014):
-
- 16.6 Pragma-Direktive [cpp.pragma]
- C++11 Standard (ISO/IEC 14882:2011):
-
- 16.6 Pragma-Direktive [cpp.pragma]
- C++98-Standard (ISO/IEC 14882:1998):
-
- 16.6 Pragma-Direktive [cpp.pragma]
Siehe auch
|
C-Dokumentation
für
Implementierungsdefiniertes Verhalten Steuerung
|
Externe Links
| 1. | C++-Pragmas in Visual Studio |
| 2. | Pragmas von GCC unterstützt |
| 3. | Einzelne Pragmabeschreibungen und Standard-Pragmas in IBM AIX XL C 16.1 |
| 4. | Anhang B. Pragmas im Sun Studio 11 C++ Benutzerhandbuch |
| 5. | Intel C++ Compiler-Pragmas |
| 6. | Release-Knoten (enthält Pragmas) für HP aCC A.06.25 |