BEARBEITEN: microtherion gibt eine hervorragende Antwort, die einige meiner Punkte hier korrigiert, insbesondere in Bezug auf die Speichernutzung.
Wie Sie festgestellt haben, gibt es bestimmte Situationen, in denen Sie zur Verwendung von a gezwungen sind #define
, da der Compiler keine const
Variablen zulässt . In einigen Situationen sind Sie gezwungen, Variablen zu verwenden, z. B. wenn Sie ein Array von Werten benötigen (dh Sie können kein Array von Werten haben #define
).
Es gibt jedoch viele andere Situationen, in denen nicht unbedingt eine einzige „richtige“ Antwort vorliegt. Hier sind einige Richtlinien, denen ich folgen würde:
Typensicherheit Im
Hinblick auf die allgemeine Programmierung const
sind Variablen in der Regel vorzuziehen (soweit möglich). Der Hauptgrund dafür ist die Typensicherheit.
Ein #define
(Präprozessor-Makro) kopiert den Literalwert direkt an jede Stelle im Code, wodurch jede Verwendung unabhängig wird. Dies kann hypothetisch zu Mehrdeutigkeiten führen, da der Typ je nach Verwendungszweck unterschiedlich aufgelöst werden kann.
Eine const
Variable ist immer nur ein Typ, der durch ihre Deklaration bestimmt und bei der Initialisierung aufgelöst wird. Es wird oft eine explizite Besetzung erfordern, bevor es sich anders verhält (obwohl es verschiedene Situationen gibt, in denen es sicher implizit vom Typ heraufgestuft werden kann). Zumindest kann der Compiler (bei korrekter Konfiguration) eine zuverlässigere Warnung ausgeben, wenn ein Typproblem auftritt.
Eine mögliche Problemumgehung besteht darin, eine explizite Umwandlung oder ein Typ-Suffix in ein einzuschließen #define
. Beispielsweise:
#define THE_ANSWER (int8_t)42
#define NOT_QUITE_PI 3.14f
Dieser Ansatz kann jedoch in einigen Fällen möglicherweise zu Syntaxproblemen führen, je nachdem, wie er verwendet wird.
Speichernutzung
Im Gegensatz zum Allzweck-Computing hat Speicher offensichtlich einen hohen Stellenwert im Umgang mit so etwas wie einem Arduino. Die Verwendung einer const
Variablen im Vergleich zu einer #define
kann sich darauf auswirken, wo die Daten im Speicher gespeichert sind, wodurch Sie möglicherweise gezwungen werden, die eine oder andere zu verwenden.
const
Variablen werden (normalerweise) zusammen mit allen anderen Variablen im SRAM gespeichert.
- Literalwerte, die in verwendet werden,
#define
werden häufig im Programmbereich (Flash-Speicher) neben der Skizze selbst gespeichert.
(Beachten Sie, dass es verschiedene Faktoren gibt, die genau beeinflussen können, wie und wo etwas gespeichert wird, z. B. die Compilerkonfiguration und -optimierung.)
SRAM und Flash haben unterschiedliche Einschränkungen (zB 2 KB bzw. 32 KB für das Uno). Für einige Anwendungen ist es recht einfach, kein SRAM mehr zu haben. Daher kann es hilfreich sein, einige Dinge in Flash zu verschieben. Das Gegenteil ist auch möglich, wenn auch wahrscheinlich weniger verbreitet.
PROGMEM
Es ist möglich, die Vorteile der Typensicherheit zu nutzen und gleichzeitig die Daten im Programmspeicher (Flash) zu speichern. Dies geschieht mit dem PROGMEM
Schlüsselwort. Es funktioniert nicht für alle Typen, wird jedoch häufig für Arrays von ganzen Zahlen oder Zeichenfolgen verwendet.
Die allgemeine Form in der Dokumentation ist wie folgt:
dataType variableName[] PROGMEM = {dataInt0, dataInt1, dataInt3...};
String-Tabellen sind etwas komplizierter, aber die Dokumentation enthält alle Details.