const int led = 13;
To jest poprawna metoda. Lub nawet:
const byte led = 13;
Ile masz szpilek?
Niektóre samouczki nie poddały się tak dużej kontroli jakości, jak mogą.
Wydajność będzie lepsza w użyciu const byte
, w porównaniu z int
tym, że kompilator może być wystarczająco inteligentny, aby zrozumieć, co robisz.
To, co możesz zrobić, to delikatnie zachęcić ludzi do korzystania z bardziej wydajnych technik, używając ich we własnym kodzie.
Odpowiedzi na komentarze
byte
Komentator zasugerował, że nie jest to standard C. Jest to poprawne, jednak jest to strona Arduino StackExchange i uważam, że użycie standardowych typów dostarczanych przez Arduino IDE jest dopuszczalne.
W Arduino.h jest ta linia:
typedef uint8_t byte;
Pamiętaj, że nie jest to dokładnie to samo co unsigned char
. Zobacz uint8_t vs unsigned char i Kiedy uint8_t ≠ unsigned char? .
Inny komentator zasugerował, że użycie bajtu niekoniecznie poprawi wydajność, ponieważ liczby mniejsze niż int
będą promowane int
(patrz Zasady promocji liczb całkowitych, jeśli chcesz więcej na ten temat).
Jednak w kontekście identyfikatora stałej kompilator generuje wydajny kod w każdym przypadku. Na przykład deasemblacja „mrugnięcia” daje to w oryginalnej formie:
00000086 <loop>:
86: 8d e0 ldi r24, 0x0D ; 13
88: 61 e0 ldi r22, 0x01 ; 1
8a: 1b d1 rcall .+566 ; 0x2c2 <digitalWrite>
W rzeczywistości generuje ten sam kod, czy 13
:
- Jest dosłowne
- Jest
#define
- Jest
const int
- Jest
const byte
Kompilator wie, kiedy może zmieścić liczbę w jednym rejestrze, a kiedy nie. Jednak dobrą praktyką jest stosowanie kodowania, które wskazuje na twoje zamiary . Wyjaśnienie tego const
jasno pokazuje, że liczba się nie zmieni, a wyjaśnienie byte
(lub uint8_t
) wyjaśnia, że oczekujesz małej liczby.
Mylące komunikaty o błędach
Innym ważnym powodem, dla którego należy unikać, #define
są komunikaty o błędach wyświetlane w przypadku pomyłki. Rozważmy ten szkic „mrugnięcia”, który zawiera błąd:
#define LED = 13;
void setup() {
pinMode(LED, OUTPUT); // <---- line with error
}
void loop() {
digitalWrite(LED, HIGH); // <---- line with error
delay(1000);
digitalWrite(LED, LOW); // <---- line with error
delay(1000);
}
Na powierzchni wygląda OK, ale generuje te komunikaty o błędach:
Blink.ino: In function ‘void setup()’:
Blink:4: error: expected primary-expression before ‘=’ token
Blink:4: error: expected primary-expression before ‘,’ token
Blink:4: error: expected `;' before ‘)’ token
Blink.ino: In function ‘void loop()’:
Blink:8: error: expected primary-expression before ‘=’ token
Blink:8: error: expected primary-expression before ‘,’ token
Blink:8: error: expected `;' before ‘)’ token
Blink:10: error: expected primary-expression before ‘=’ token
Blink:10: error: expected primary-expression before ‘,’ token
Blink:10: error: expected `;' before ‘)’ token
Patrzysz na pierwszą podświetloną linię (linia 4) i nawet nie widzisz symbolu „=”. Dodatkowo linia wygląda dobrze. Teraz dość oczywiste jest, na czym polega problem ( = 13
jest zastępowany LED
), ale gdy linia znajduje się 400 linii dalej w kodzie, nie jest oczywiste, że problem dotyczy sposobu definiowania diody LED.
Widziałem ludzi zakochanych wiele razy (w tym siebie).