Чому в int всього 2 байти?


9

При використанні C / C ++ на інших платформах intтип, як правило, становить 4 байти (або потенційно більше). Однак на Arduino це лише 2 байти.

Чому це різне? Чи впливає це на продуктивність, якщо я завжди використовую 4 байти longзамість цього?


2
зауважте, що intце 4 байти на Arduino Due. A shortбуде 2 байти на всіх існуючих Ardunios, але я наголошую на порадах інших щодо використання int16_tабо uint16_t.
Рон

Відповіді:


10

ATmega328, який використовується в багатьох Arduinos, є 8-бітовим мікроконтролером. Це означає, що регістри є 8-бітними, шина даних - 8-бітовою, порти - 8-бітними. У системі є мінімальні 16-бітні аспекти (наприклад, один із таймерів), але майже все є 8-бітним.

Тому більшість операцій одночасно обробляють 8-бітні. Робота над чим-небудь, крім 8-бітових (тобто 16-бітних або 32-бітових цілих чисел та чисел з плаваючою комою), вимагає того, що по суті може бути описано як емуляція програмного забезпечення, де компілятор використовує кілька інструкцій для роботи над цими більшими змінними.

8-біт очевидно достатній для адреси 8-бітового порту. Досить також мати справу з багатьма лічильниками циклів, значеннями повернення та символами ASCII. Це насправді недостатньо, хоча при роботі з цифрами. Підписаний 8-розрядний int (int8_t) може представляти лише -128 -> +127. Непідписаний (uint8_t) може представляти лише 0 -> 255.

8-бітні цілі числа є досить обмежуючими. C / C ++ int повинен представляти щонайменше -32,678 -> +32,767, тому карти на int16_t - найменший розмір, який це зробить. Це дає хороший баланс дальності та ефективності. Це особливо важливо, коли початківці навчаються - переповнення насправді не те, що розуміють непрограмісти.

Однак це має вплив на продуктивність, оскільки більшість 16-бітних операцій займають щонайменше вдвічі довше, ніж 8-бітова операція, і використовують вдвічі більше регістрів. Це може не вплинути на вас.

Багато з нас переходять на рідні типи, такі як int8_t та uint8_t, оскільки це дає набагато більше контролю.


3
Лише зауваження: це не команда Arduino, яка зіставила int на int16_t, "int" - це зарезервоване ключове слово C / C ++, а відображення типу є частиною ABI ( gcc.gnu.org/wiki/avr-gcc ), що Розробники компілятора avr-gcc вирішили дотримуватися. Ще одна помітна відмінність - у "подвійному" типі, який зазвичай має ширину 64 біт, тоді як у avr-gcc 32-
бітовий

Дякую. Не впевнений, чому я це написав. Я знаю, що int повинен представляти 32,678 -> +32,767 (хоча, власне, я думаю, що був власний компілятор для одного з процесорів NEC, який не дотримувався цього). Я думаю, це тому, що мені не подобається приховувати ширину вбудованих систем - використання int16_t набагато зрозуміліше.
Кібергіббони

1
+1 за використання чітких рідних типів! На Arduino Due int32-бітний! arduino.cc/en/Reference/int
Рон

3

Важливим фактом щодо мов C та C ++ є те, що їхні відповідні стандарти не визначають розмір (у байтах) інтегральних типів та типів з плаваючою комою.

Вони просто визначають мінімальні діапазони та відношення між цими діапазонами, наприклад

range(short) <= range(int) < range(long)

Отже, розмір, наприклад, intзаповіту, як правило, залежить від:

  • цільова платформа (процесор)
  • сам компілятор

ти кажеш, що sizeof(short) == sizeof(int) == sizeof(long)це можливо?
Рон

@ ron-e Теоретично, так, це було б можливо. На практиці, однак, я ніколи цього не бачив. У більшості компіляторів / платформ можна було очікувати (хоча це не нав'язується) цього sizeof(short) < sizeof(long).
jfpoilpret
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.