Что такое переменные в Arduino. Как объявлять переменные разных типов данных. Какие существуют ограничения при именовании переменных. В чем отличие глобальных и локальных переменных. Как использовать статические переменные.
Что такое переменные в Arduino и зачем они нужны
Переменная в Arduino — это именованный контейнер для хранения данных, значение которого может меняться в процессе выполнения программы. Переменные используются для:
- Хранения промежуточных результатов вычислений
- Передачи данных между разными частями программы
- Отслеживания состояния устройств (например, положения сервопривода)
- Накопления данных с датчиков
- Задания параметров работы устройств
Использование переменных делает код более гибким и удобным для модификации. Вместо жестко заданных значений можно использовать переменные, изменяя которые легко настроить работу устройства.
Основные типы данных переменных в Arduino
Arduino поддерживает следующие основные типы данных для переменных:
- int — целые числа от -32768 до 32767 (16 бит)
- long — целые числа от -2147483648 до 2147483647 (32 бита)
- float — числа с плавающей точкой (32 бита)
- double — числа с плавающей точкой двойной точности (64 бита)
- char — символы в кодировке ASCII
- boolean — логический тип (true/false)
Также есть производные типы:
- byte — целые числа от 0 до 255 (8 бит)
- word — целые числа от 0 до 65535 (16 бит)
- String — строки символов
При выборе типа данных следует учитывать диапазон значений переменной и требуемую точность. Это позволит оптимально использовать память микроконтроллера.
Как объявить переменную в Arduino
Для объявления переменной в Arduino используется следующий синтаксис:
тип_данных имя_переменной;
Например:
int sensorValue;
float temperature;
boolean ledState;
Можно также сразу присвоить переменной начальное значение:
int counter = 0;
float pi = 3.14;
char letter = 'A';
Объявление переменной создает для нее ячейку в памяти и позволяет обращаться к ней по имени в дальнейшем коде.
Правила именования переменных в Arduino
При выборе имен для переменных следует придерживаться следующих правил:
- Имя должно начинаться с буквы или знака подчеркивания
- Последующие символы могут быть буквами, цифрами или знаком подчеркивания
- Нельзя использовать пробелы и спецсимволы
- Нельзя использовать зарезервированные слова языка (например, int, for, if)
- Имена чувствительны к регистру (myVariable и myvariable — разные переменные)
Рекомендуется использовать осмысленные имена, отражающие назначение переменной. Например, ledPin лучше, чем просто x.
Глобальные и локальные переменные в Arduino
В Arduino переменные могут быть глобальными или локальными:
- Глобальные переменные объявляются вне всех функций и доступны из любого места программы. Они существуют все время работы скетча.
- Локальные переменные объявляются внутри функций и существуют только во время выполнения этой функции. Они недоступны из других частей программы.
Пример:
int globalVar = 10; // Глобальная переменная
void setup() {
int localVar = 5; // Локальная переменная
// ...
}
void loop() {
globalVar++; // Доступ к глобальной переменной
// localVar++; // Ошибка - localVar не существует здесь
}
Рекомендуется использовать локальные переменные везде, где это возможно, чтобы избежать случайного изменения значений из других частей программы.
Статические переменные в Arduino
Статические переменные — это особый вид локальных переменных, которые сохраняют свое значение между вызовами функции. Они объявляются с ключевым словом static:
void myFunction() {
static int counter = 0;
counter++;
Serial.println(counter);
}
При каждом вызове myFunction() значение counter будет увеличиваться на 1, а не сбрасываться в 0.
Статические переменные полезны, когда нужно сохранять состояние между вызовами функции, но не делать переменную глобальной.
Константы в Arduino
Константы — это переменные, значение которых нельзя изменить после инициализации. Они объявляются с ключевым словом const:
const int ledPin = 13;
const float pi = 3.14159;
Использование констант делает код более понятным и защищает от случайного изменения важных значений.
Преобразование типов переменных в Arduino
Иногда возникает необходимость преобразовать переменную одного типа в другой. Для этого используется операция приведения типа:
int intValue = 65;
char charValue = (char)intValue; // Преобразование int в char
float floatValue = 3.14;
int roundedValue = (int)floatValue; // Преобразование float в int
При преобразовании следует учитывать возможную потерю точности или переполнение.
Массивы как переменные в Arduino
Массив — это набор переменных одного типа, доступных под общим именем. Массивы объявляются следующим образом:
int myArray[5]; // Массив из 5 целых чисел
float sensorValues[10]; // Массив из 10 чисел с плавающей точкой
Элементы массива нумеруются с 0. Обращение к элементам происходит по индексу:
myArray[0] = 42;
float value = sensorValues[3];
Массивы удобны для хранения наборов связанных данных, например, показаний нескольких датчиков.
Область видимости переменных в Arduino
Область видимости определяет, где в программе можно использовать переменную. В Arduino есть следующие области видимости:
- Глобальная область — переменные доступны везде в программе
- Область функции — локальные переменные доступны только внутри функции
- Область блока — переменные, объявленные внутри фигурных скобок, доступны только в этом блоке
Пример:
int globalVar = 10; // Глобальная переменная void setup() { int setupVar = 5; // Доступна только в setup() if (true) { int blockVar = 3; // Доступна только в этом блоке if } // blockVar здесь уже не существует } void loop() { globalVar++; // Можно использовать глобальную переменную // setupVar и blockVar здесь недоступны }
Правильное использование областей видимости помогает организовать код и избежать конфликтов имен переменных.
Оптимизация использования памяти при работе с переменными
Микроконтроллеры Arduino имеют ограниченный объем памяти, поэтому важно оптимально использовать переменные:
- Используйте наименьший подходящий тип данных (например, byte вместо int для малых чисел)
- Освобождайте память, удаляя ненужные переменные
- Используйте локальные переменные вместо глобальных, где это возможно
- Применяйте структуры данных для группировки связанных переменных
- Используйте PROGMEM для хранения констант в программной памяти
Следование этим принципам позволит эффективнее использовать ограниченные ресурсы микроконтроллера.
Типы данных в Python — Робикс кружок робототехники
Главная › База знаний › Программирование › Python › Числовые типы данных в Python: integer, float
Переменные
Любые данные хранятся в ячейках памяти компьютера. Когда мы вводим число, оно помещается в какую-либо ячейку памяти. Возникают вопросы: Куда именно? Как впоследствии обращаться к этим данными?
В программе данные связываются с каким-либо именем. В дальнейшем обращение к ним возможно по этому имени-переменной.
Термин «переменная» обозначает, что ее сущность может меняться, она непостоянна.
В программе на языке Python, как и на большинстве других языков, связь между данными и переменными устанавливается с помощью знака = (знак равно). Данная операция называется присваиванием.
Например, выражение, представленное ниже, означает, что на объект, представляющий собой число 4, находящееся в определенной области памяти, теперь ссылается переменная a.
Имена переменных могут быть любыми. Однако есть несколько общих правил их написания:
- Желательно давать переменным осмысленные имена, говорящие о назначении данных, на которые они ссылаются.
- Имя переменной не должно совпадать с командами языка (зарезервированными ключевыми словами).
- Имя переменной должно начинаться с буквы или символа подчеркивания, но не с цифры.
- Имя переменной не должно содержать пробелы.
Чтобы узнать значение, на которое ссылается переменная, находясь в режиме интерпретатора, достаточно ее вызвать, то есть написать имя и нажать Enter.
Числовые типы данных
Напишите в консоли следующую команду и нажмите Enter:
>>> 1 + 1
В результате получим следующее:
При программировании мы чаще всего будем сталкиваться с такими числовыми типами данных (формализация информации), как целые числа и числа с плавающей точкой.
Целые числа (тип int) — это положительные и отрицательные целые числа, а также 0, например: 0, -1, 1, 1827 и т. д.
Числа с плавающей точкой (тип float) — это вещественные, числа (рациональные + иррациональные числа), например: 0, -1, 1, 1827, 0.5, -0.76, 3.141592 (число пи) и т.д.
Операции
Операция — это выполнение каких-либо действий над данными (операндами). Действие выполняется оператором (сложение(+), умножение(*) и т.п. ). Результат операции зависит как от оператора, так и от операндов.
Изменение типа переменных
Давайте создадим две переменные A и B, которым присвоим некоторые значения:
>>> A = 10 >>> B = 1.24
В зависимости от введенной информации, Python самостоятельно определяет тип переменно. Чтобы посмотреть типы заданных переменных, воспользуемся функцией type(), для этого введем следующую команду:
>>> type(A)
После ввода на экране появится тип переменной А, в нашем случае это будет целое число, то есть на экране мы увидим следующее:
>>> type(A) <class 'int'>
Проведем ту же операцию со второй переменой, на экране увидим следующее:
>>> type(B) <class 'float'>
Попробуем сложить переменные разных типов данных и выясним, к какому типу относится полученный результат:
>>> С = A + B >>> type(С) <class 'float'>
Как можете заметить, в итоге мы получили переменную float.
Любые математические действия можно выполнять только над одинаковыми типами данных, т.е. либо все float, либо все int и т.д.
Но тогда как мы сейчас смогли это сделать? Python самостоятельно производит перевод переменных в нужный тип данных. Вы можете самостоятельно произвести данный переход с помощью функций int(), float():
>>> type(A) <class 'int'> >>> A = float(A) >>> type(A) <class 'float'> >>> type(B) <class 'float'> >>> B = int(B) >>> type(B) <class 'int'> >>> A 10.0 >>> B 1
Как видите, значение B было округлено. Рассмотрим подробнее округление на функции int(), которая переводит вещественное число в целое:
>>> A1 = 0.1 >>> A2 = 0.4 >>> A3 = 0.7 >>> A4 = 1.1 >>> A1 = int(A1) >>> A2 = int(A2) >>> A3 = int(A3) >>> A4 = int(A4) >>> A1 0 >>> A2 0 >>> A3 0 >>> A4 1
Как можно заметить, округление происходит до ближайшего целого числа по направлению в сторону нуля, то есть в меньшую сторону.
Основные математические операции в Python
- Cложение (+) используется для получения суммы (в отношении чисел), было нами рассмотрено выше.
- Вычитание (-) — операция, противоположная сложению.
- Умножение(*) используется для получения произведения сомножителей.
>>> type(2 * 2) <class 'int'> >>> type(0.1 * 2) <class 'float'> >>> type(0.2 * 5) <class 'float'>
- Возведение в степень (**) используется для возведения числа в степень, то есть умножение числа на само себя столько раз, сколько указано в степени.
>>> 2 ** 3 8 >>> 2 ** 4 16
- Деление (/) — действие, обратное умножению, используется для получения частного
>>> 4 / 2 2.0 >>> type(4/2) <class 'float'> >>> 2 / 4 0.5
Даже если делимое и делитель являются целыми числами и делитель содержится в делимом целое число раз, то результат деления будет float.
- Целочисленное деление (//) нужно для получения целочисленного результата деления, то есть при данной операции отбрасывается дробная часть числа.
>>> 4 // 2 2 >>> type(4 / 2) <class 'float'> >>> 2//4 0 >>> type(2 // 4) <class 'int'>
- Получение остатка от деления (%). В результате данной операции Вы получаете то, что осталось от деления, то есть вы получаете то, что невозможно дальше делить. Например, в первом случае 4 делится без остатка — в 4 две 2, во втором случае 2 не разделить на 4, оно сразу уходит в остаток, в третьем случае 7 содержит две 3 (6), в остаток уходит 7 — 6 = 1.
>>> 4 % 2 0 >>> 2 % 4 2 >>> 7 % 3 1
- Модуль числа (abs()) используется для получения модуля числа, то есть отбрасывается знак перед числом
>>> abs(-0.1) 0.1 >>> abs(0) 0 >>> abs(-283) 283 >>> abs(45) 45
- Округление (round()) — данная операция округляет число до ближайшего целого числа, формат int.
>>> round(0.5) 0 >>> round(0.6) 1 >>> round(1.1) 1 >>> round(1.5) 2 >>> round(1.4) 1
Курсы Робикс, в которых изучается этот материал.
- Программирование на Python в Minecraft
- Duckietown робот с системой Автопилота
Сохраните или поделитесь
Переменные в программировании Arduino (упрощенное руководство)
До сих пор в наших руководствах мы достаточно освещали темы, которые познакомили нас с Arduino, теперь; мы углубляемся в изучение.
В этом уроке; Переменные в программировании Arduino, мы изучим следующее:
- Переменная как контейнер значений
- Природа переменных
- Типы данных переменных
- Объявление и инициализация переменных
- Ограничения идентификации именования переменных
- Соглашения об именах переменных «CamelCase»
- Определения типов переменных данных
- Область действия переменной
Быстрая навигация
VARIABLE AS VALUE-CONTAINER
В английском языке переменная относится к чему-то, что может измениться; константа — это то, что не изменяется. В программировании Arduino переменная представляет собой «контейнер именованных значений », в котором могут храниться значения. Эти значения могут меняться со временем, поэтому они называются переменными, но имя сущности, содержащей переменную, не меняется.
С другой стороны, мы можем видеть переменную как ведро; вода как предмет может быть очищена в ведро и удалена из ведра. Кроме того, это ведро может содержать различные типы предметов, вы можете решить заполнить ведро камнями или чем угодно, если хотите, чтобы ведро вмещало то, что в нем.
Переменные используются для переноса данных из одной части программы в другую часть программы. Содержимое переменной может измениться; однако в программировании идентификатор или имя переменной остается прежним.
Рисунок 1: Переменная как контейнер материала ПРИРОДА ПЕРЕМЕННЫХПеременная должна иметь имя и быть типа данных. Когда переменная представляет собой просто целочисленную переменную, это означает, что значение, которое будет храниться в переменной, является целым числом.
У нас могут быть другие типы данных, такие как: float , char , double , Boolean и т. д. Мы обсудим их в будущем, но просто знайте, что переменная содержит или сохраняет данные определенного типа . Например, предположим, что мы разработали и запрограммировали схему для измерения расстояния до автомобиля-робота по мере его приближения к препятствию, вы можете решить интегрировать дисплей, чтобы показать расстояние, на котором автомобиль находится от препятствия, можно заметить, что отображаемые значения меняются по мере того, как роботизированный автомобиль приближается или удаляется от препятствия.
Тот, кто программировал роботизированную машину, должен был создать в микроконтроллере область памяти в качестве переменной для хранения измеряемых данных, поскольку эти данные должны будут изменяться по мере движения роботизированной машины, они будут вычисляться и записываться как переменные . Эти записанные данные должны быть записаны как данные определенного типа. Если тип данных, который был запрограммирован, является целым числом, то результат, который будет отображаться на экране, будет целочисленным значением, но если он был запрограммирован для отображения типа данных с плавающей запятой или двойного числа, в результате также будет отображаться десятичная точка. .
ТИПЫ ПЕРЕМЕННЫХ ДАННЫХПри программировании Arduino вы должны указать тип данных любой переменной, которую вы используете в программе, и всякий раз, когда вы хотите изменить содержимое переменной, вы должны убедиться, что придерживаетесь определенного тип данных, который вы объявили для переменной в начале. В остальном, чтобы хорошо понять концепцию типов данных, давайте посмотрим на рисунок ниже.
Рисунок 2: Различные контейнеры, символизирующие различные типы переменных данныхКак уже говорилось ранее, существуют различные типы данных, в том числе целочисленные, символьные, строковые, логические, плавающие, двойные и т. д. Рисунок выше дает интуитивное представление о том, какие типы данных выглядят нравиться. У нас есть различные контейнеры различной формы, предназначенные для хранения предметов с определенными характеристиками, первая фигура представляет собой контейнер прямоугольной формы, предназначенный для хранения прямоугольных предметов. Если этот контейнер (переменная) является целым числом, он будет принимать только целые данные (кубоиды), в нашей аналогии, контейнер предназначен специально для хранения прямоугольных фигур, помещение любого другого типа данных в эту уникальную целочисленную переменную будет ошибочным, то же самое вещь применима к другим контейнерам.
ОБЪЯВЛЕНИЕ ПЕРЕМЕННОЙ И ИНИЦИАЛИЗАЦИЯЧтобы объявить переменную в программировании Arduino, требуется всего два простых шага.
Шаг 1: Укажите тип данных переменной
Шаг 2: Укажите имя переменной
См. рисунок ниже.
Рисунок 3: Простые объявления переменных в программировании ArduinoНа приведенном выше рисунке строки кода с 1 по 6 являются строками кода объявления переменных, вы можете видеть, что типы данных отображаются другим цветом, а имена переменных отображаются другим цветом. Arduino IDE была разработана для отображения типов данных таким цветом, чтобы отличать их от других слов, используемых при написании программы. Вы можете передать данные в переменную сразу после объявления переменной, этот процесс передачи данных в переменную сразу после ее объявления называется инициализацией переменной, см. рис. 4 ниже.
Рисунок 4: Данные, передаваемые в переменные ОГРАНИЧЕНИЯ НА ИМЕНИ ИДЕНТИФИКАЦИИ ПЕРЕМЕННЫХВы можете назвать переменную произвольно; Однако действуют следующие ограничения.
- Имя переменной не может содержать пробелы или специальные символы; однако вы можете использовать подчеркивание. Например. «my_Num» может служить именем переменной, но не my#name.
- В имени переменной может быть число, например. my8num, но число не может начинаться с имени переменной, например. 9myNum неприемлем, и вы не можете использовать просто число для имени переменной.
- Имя переменной не может быть именем ключевого слова arduino, например. void, int, delay, loop и т. д.
Имя переменной должно быть описательным и понятным; это должно быть слово, значение которого понял бы другой человек, читающий эскиз. Это должно быть слово, употребление которого вы сможете вспомнить даже по прошествии года.
Например, если вы хотите назвать цифровой контакт (который можно хранить в переменном держателе), к которому вы подключили светодиод на плате Arduino, вы можете использовать любое слово, которое вам нравится, если оно не нарушает исключительных правил. выше, однако, выбор имени типа « cool » в качестве имени переменной цифрового вывода не является проблемой, но, если вы вернетесь к скетчу через год, вы легко вспомните, что переменная « cool » в ваш эскиз относится к цифровому выводу, к которому вы подключили светодиод в своем дизайне ??? Я сомневаюсь, что вы легко можете!
С другой стороны, если вы назвали переменная « ledPin » даже после 10 лет, вы все еще можете помнить, что это относится к контакту, на котором находится светодиод. связанный. Поэтому использование описательных идентификаторов переменных очень необходимо. в объявлении переменной.
NB: идентификатор переменной означает переменную name
Кроме того, добавление комментариев к переменной для объяснения ее значения является дополнительным бонусом. Вы можете проверить учебник о том, как добавить комментарии к эскизу Arduino.
Существует соглашение, используемое для именования переменных в программировании, оно называется CamelCase (также «верблюжий случай» или «верблюжий случай»). Это соглашение об именах, в котором первая буква каждого слова в составном слове пишется с заглавной буквы. Примеры включают ledPin, pushButton, buttonState, switchPin и т. д., что делает имя легко читаемым.
Когда мы указываем тип данных, мы сообщаем компилятору выделить определенный объем памяти для хранения данных, которые мы отправляем в это так, если вы попросите компилятор сохранить данные, которые не предназначены для типа данных, который он может содержать, это становится проблемой, поэтому мы должны строго поддерживать формат при изменении содержимого переменных, мы должны это сделать относительно типа данных переменной.
ОПРЕДЕЛЕНИЯ ТИПОВ ПЕРЕМЕННЫХ ДАННЫХВ таблице ниже показаны различные типы данных и их определения
ИМЯ | КРАТКОЕ ОПРЕДЕЛЕНИЕ |
void | Used only in function declarations- it means returns nothing |
boolean | Holds either 1 or 0, true or false, LOW or HIGH |
char | -128 to 127 and character литералы |
unsigned char | 0-225 |
byte | 0-225 |
int | -32,768 to 32,768 |
unsigned int | 65,555 |
word | 65,555 |
long | -2,147,483,648 to 2,147,483,647 |
unsigned long | 0 to 4,294,967,295 |
float | -3.4028235E+38to3. 4028235E+38 |
double | -3.4028235E+38to3.4028235E+38 |
строка | Массив символов, определяемый как char strName[5]; |
String | AStringObject |
- Глобальная переменная
- Локальная переменная
ЧТО ТАКОЕ ГЛОБАЛЬНАЯ ПЕРЕМЕННАЯ?
Глобальная переменная — это простая переменная, которую может видеть каждая функция в программе.
ЧТО ТАКОЕ ЛОКАЛЬНАЯ ПЕРЕМЕННАЯ?
С другой стороны, локальные переменные видны только функциям, в которых они объявлены. В среде разработки Arduino любая переменная, объявленная вне функции, такой как setup(), loop() и т. д., является глобальной переменной.
Когда программы становятся больше и сложнее, локальные переменные становятся полезным инструментом, гарантирующим, что только одна функция имеет доступ к своей собственной переменной. Это помогает свести к минимуму ошибку программы, когда одна функция по незнанию изменяет переменные, используемые другой функцией.
Рисунок 6: Глобальные и локальные переменныеСтроки кода с 1 по 6 — глобальные переменные, а строки кода 15 и 16 — локальные переменные.
Прочитав и понял этот урок, теперь откройте несколько примеров скетчей в arduino IDE и проверьте, как используются переменные. Следите за следующим уроком.
21. Что такое «статическая» переменная и как ее использовать
Серия руководств по программированию Arduino
Язык C содержит специальные ключевые слова, которые изменяют поведение переменной. Одним из них является ключевое слово «статический». То, как это работает, неочевидно, поэтому я провел серию экспериментов, чтобы помочь вам понять.
Статическая переменная используется для сохранения значения переменной. Когда вы помечаете переменную как статическую, ее значение сохраняется в вашей программе до завершения программы.
Думайте о статической переменной, как если бы она была глобальной с уменьшенной областью действия. Глобальная переменная имеет глобальную область действия и сохраняется до тех пор, пока выполняется программа. Статическая переменная имеет локальную область действия, но также сохраняется до тех пор, пока работает программа.
Обычно вы используете статическую переменную в тех случаях, когда хотите сохранить значение переменной внутри функции. Обычные локальные переменные уничтожаются, когда функция завершается, и пересоздаются/создаются при вызове функции.
Давайте рассмотрим пример, который поможет понять поведение статической переменной.
Рассмотрим этот код, «образец A», который вы можете получить на Github:
Загрузите скетч на Arduino и откройте последовательный монитор. Монитор отобразит этот вывод:
В_функция: 0
В_функция: 0
В_функция: 0
В_функция: 0
В_функция: 0
В_функция: 0
В_функция: 0
В_функция: 0
3
23
2323
2323 Счетчик остается «0», потому что каждый раз, когда
вызывается a_fuction , локальная переменная local_variable повторно объявляется и повторно инициализируется в «0». Несмотря на то, что в строке 16 значение локальной переменной увеличивается на единицу, новое значение теряется.
Теперь рассмотрим этот код, «пример B», который вы можете получить на Github:
Загрузите скетч на Arduino и откройте последовательный монитор. Монитор покажет этот вывод:
В функции_а: 0
В цикле: 1
В функции_а: 1
В цикле: 2
В_функции: 2
В цикле: 3
В_функции: 3
В цикле: 4
В_функции: 4
В цикле: 5
В_функции: 5
В цикле: 6
В_функции: 6
В цикле: 7
В функции_а: 7
В цикле: 8
В функции_а: 8
В цикле: 9
В функции_а: 9
В цикле: 10 и инициализировать ее в строке 1. Несмотря на то, что это глобальная переменная, я решил сохранить исходное имя, чтобы сохранить преемственность между примерами.
Поскольку значение local_variable увеличивается внутри a_function , а не повторно инициализируется (как это было в исходной версии скетча), значение не теряется. Он сохраняется при последующих вызовах функции a_function .
Теперь рассмотрим следующий вариант кода, «образец C», который вы можете получить на Github:
Загрузите скетч на Arduino и откройте последовательный монитор. Монитор покажет этот вывод:
В функции_а: 0
В цикле: 1
В функции_а: 1
В цикле: 2
В функции_а: 2
В цикле: 3
В функции_а: 3
В цикле: 4
В функции_а: 4
В цикле: 5
В функции_а: 5
В цикле: 6
В функции_а: 6
В цикле: 7
В функции_а: 7
В цикле: 8
В функции_а: 8
В цикле: 9
В функции_а: 9
В цикле: 10
Единственная разница между эскизами вариантов В и С состоит в том, что в С переменная local_variable помечен как статический.
Вывод двух эскизов идентичен.
Наконец, рассмотрим последний вариант кода, «пример D», который вы можете получить на Github:
Загрузите скетч на Arduino и откройте последовательный монитор. Монитор отобразит этот вывод:
В_функция: 0
В_функция: 1
В_функция: 2
В_функция: 3
В_функция: 4
В_функция: 5
В_функция: 6
В_функция: 7
В_функции: 8
В_функции: 9
В_функции: 10
Разве это не интересно?
В примере D переменная local_variable помечена как статическая, но на этот раз объявлена внутри функции a_function . В соответствии с первым экспериментом вы ожидаете, что последовательный монитор покажет нули, поскольку переменная повторно инициализируется в строке 13.
Но это не так.
Поскольку локальная_переменная помечена как статическая, ее значение сохраняется, когда функция завершает свое выполнение. Он не инициализируется повторно при повторном вызове той же функции.
Когда содержимое статической переменной исчезнет? Когда программа завершается, точно так же, как это происходит для глобальной переменной.
Подведем итоги этих экспериментов.
В образце A распечатка монитора показывает, что переменная всегда равна 0. Мы ожидали, что переменная определена и инициализирована внутри функции. Каждый раз, когда функция вызывается в цикле, переменная переопределяется и инициализируется до 0.
В образце B переменная local_variable является глобальной. Как и ожидалось, к нему имеют доступ и функции цикла, и функции a_function. После инициализации оно увеличивается на 1 внутри a_function, и одно и то же значение выводится на монитор из внутреннего цикла и a_function.
В примере C мы пометили local_variable как статическую, и из-за ее положения она по-прежнему доступна глобально. Распечатка, которую мы получаем, идентична той, которую мы получили из образца B. Объявление этой глобальной переменной как статической не влияет на результат. Компилятор может даже игнорировать этот модификатор.
Наконец, в примере D мы перемещаем объявление переменной внутрь функции a_function. На данный момент эскиз идентичен эскизу образца A. Но в образце D мы используем модификатор static. Распечатка последовательного монитора показывает, что значение переменной сохраняется между вызовами a_function.
Каков практический урок всего этого?
1. Если вы хотите сохранить состояние переменной в программе, вы можете создать ее как глобальную переменную. Пометка его как статического не меняет того факта, что значение переменной будет сохраняться на протяжении всей жизни программы. Однако глобальная переменная может быть доступна в любом месте программы, и это может привести к ошибкам. В больших программах и из-за того, что у большинства любителей Arduino нет доступа к отладчику, лучше не использовать глобальную переменную, если доступ к ней действительно не требуется глобально.
2. Если вы хотите сохранить состояние локальной переменной функции, пометьте ее как статическое. Вы получите все преимущества глобально объявленной переменной без проблем, описанных в пункте 1.
Впервые в Arduino?
Arduino Step by Step Getting Started — наш самый популярный курс для начинающих.
Этот курс содержит высококачественное видео, мини-проекты и все необходимое для изучения Arduino с нуля. Мы поможем вам начать работу и на каждом этапе с помощью первоклассных инструкций и нашего супер-полезного пространства для обсуждения курсов.
Узнать больше
Перейти к другой статье
Закончили с основами? Ищете более сложные темы?
Arduino Step by Step Getting Serious — это наш всеобъемлющий курс Arduino для людей, готовых перейти на следующий уровень.
Узнайте о Wi-Fi, BLE и радио, двигателях (серводвигателях, двигателях постоянного тока и шаговых двигателях с различными контроллерами), ЖК-дисплеях, OLED- и TFT-экранах с кнопками и сенсорными интерфейсами, управлении большими нагрузками, такими как реле и источники света, и о многом, НАМНОГО больше.
23 Счетчик остается «0», потому что каждый раз, когда
вызывается a_fuction , локальная переменная local_variable повторно объявляется и повторно инициализируется в «0». Несмотря на то, что в строке 16 значение локальной переменной увеличивается на единицу, новое значение теряется.Теперь рассмотрим этот код, «пример B», который вы можете получить на Github:
Загрузите скетч на Arduino и откройте последовательный монитор. Монитор покажет этот вывод:
В функции_а: 0
В цикле: 1
В функции_а: 1
В цикле: 2
В_функции: 2
В цикле: 3
В_функции: 3
В цикле: 4
В_функции: 4
В цикле: 5
В_функции: 5
В цикле: 6
В_функции: 6
В цикле: 7
В функции_а: 7
В цикле: 8
В функции_а: 8
В цикле: 9
В функции_а: 9
В цикле: 10 и инициализировать ее в строке 1. Несмотря на то, что это глобальная переменная, я решил сохранить исходное имя, чтобы сохранить преемственность между примерами.
Поскольку значение local_variable увеличивается внутри a_function , а не повторно инициализируется (как это было в исходной версии скетча), значение не теряется. Он сохраняется при последующих вызовах функции a_function .
Теперь рассмотрим следующий вариант кода, «образец C», который вы можете получить на Github:
Загрузите скетч на Arduino и откройте последовательный монитор. Монитор покажет этот вывод:
В функции_а: 0
В цикле: 1
В функции_а: 1
В цикле: 2
В функции_а: 2
В цикле: 3
В функции_а: 3
В цикле: 4
В функции_а: 4
В цикле: 5
В функции_а: 5
В цикле: 6
В функции_а: 6
В цикле: 7
В функции_а: 7
В цикле: 8
В функции_а: 8
В цикле: 9
В функции_а: 9
В цикле: 10
Единственная разница между эскизами вариантов В и С состоит в том, что в С переменная local_variable помечен как статический.
Вывод двух эскизов идентичен.
Наконец, рассмотрим последний вариант кода, «пример D», который вы можете получить на Github:
Загрузите скетч на Arduino и откройте последовательный монитор. Монитор отобразит этот вывод:
В_функция: 0
В_функция: 1
В_функция: 2
В_функция: 3
В_функция: 4
В_функция: 5
В_функция: 6
В_функция: 7
В_функции: 8
В_функции: 9
В_функции: 10
Разве это не интересно?
В примере D переменная local_variable помечена как статическая, но на этот раз объявлена внутри функции a_function . В соответствии с первым экспериментом вы ожидаете, что последовательный монитор покажет нули, поскольку переменная повторно инициализируется в строке 13.
Но это не так.
Поскольку локальная_переменная помечена как статическая, ее значение сохраняется, когда функция завершает свое выполнение. Он не инициализируется повторно при повторном вызове той же функции.
Когда содержимое статической переменной исчезнет? Когда программа завершается, точно так же, как это происходит для глобальной переменной.
Подведем итоги этих экспериментов.
В образце A распечатка монитора показывает, что переменная всегда равна 0. Мы ожидали, что переменная определена и инициализирована внутри функции. Каждый раз, когда функция вызывается в цикле, переменная переопределяется и инициализируется до 0.
В образце B переменная local_variable является глобальной. Как и ожидалось, к нему имеют доступ и функции цикла, и функции a_function. После инициализации оно увеличивается на 1 внутри a_function, и одно и то же значение выводится на монитор из внутреннего цикла и a_function.
В примере C мы пометили local_variable как статическую, и из-за ее положения она по-прежнему доступна глобально. Распечатка, которую мы получаем, идентична той, которую мы получили из образца B. Объявление этой глобальной переменной как статической не влияет на результат. Компилятор может даже игнорировать этот модификатор.
Наконец, в примере D мы перемещаем объявление переменной внутрь функции a_function. На данный момент эскиз идентичен эскизу образца A. Но в образце D мы используем модификатор static. Распечатка последовательного монитора показывает, что значение переменной сохраняется между вызовами a_function.
Каков практический урок всего этого?
1. Если вы хотите сохранить состояние переменной в программе, вы можете создать ее как глобальную переменную. Пометка его как статического не меняет того факта, что значение переменной будет сохраняться на протяжении всей жизни программы. Однако глобальная переменная может быть доступна в любом месте программы, и это может привести к ошибкам. В больших программах и из-за того, что у большинства любителей Arduino нет доступа к отладчику, лучше не использовать глобальную переменную, если доступ к ней действительно не требуется глобально.
2. Если вы хотите сохранить состояние локальной переменной функции, пометьте ее как статическое. Вы получите все преимущества глобально объявленной переменной без проблем, описанных в пункте 1.
Впервые в Arduino?
Arduino Step by Step Getting Started — наш самый популярный курс для начинающих.
Этот курс содержит высококачественное видео, мини-проекты и все необходимое для изучения Arduino с нуля. Мы поможем вам начать работу и на каждом этапе с помощью первоклассных инструкций и нашего супер-полезного пространства для обсуждения курсов.
Узнать больше
Перейти к другой статье
Закончили с основами? Ищете более сложные темы?
Arduino Step by Step Getting Serious — это наш всеобъемлющий курс Arduino для людей, готовых перейти на следующий уровень.
Узнайте о Wi-Fi, BLE и радио, двигателях (серводвигателях, двигателях постоянного тока и шаговых двигателях с различными контроллерами), ЖК-дисплеях, OLED- и TFT-экранах с кнопками и сенсорными интерфейсами, управлении большими нагрузками, такими как реле и источники света, и о многом, НАМНОГО больше.