Странный глюк в массиве

rene
Offline
Зарегистрирован: 21.01.2014

Доброго времени суток!

Есть массив 

byte packHeader[] = {1, 1, 0, 0, 0, 0};

Содержимое массива с индексом 5 выдает какую то ерунду:

  Serial.println(packHeader[5], DEC);
  Serial.println();

  for (byte i = 0; i < 6; i ++) Serial.println(packHeader[i], DEC);

  Serial.println();
  Serial.println(packHeader[5], DEC);

результат выполнения:

0

1
1
0
0
0
33

0

т.е. если запрашиваешь packHeader[5], получаешь как и положено 0, а цикле этот элемент равен 33.

Как такое возможно?

Mr.Privet
Mr.Privet аватар
Offline
Зарегистрирован: 17.11.2015

Проверил на эмуляторе, все ровно выдает, так как должно быть, а не так как у Вас...

Valera19701
Valera19701 аватар
Offline
Зарегистрирован: 18.10.2015

это же не весь скетч, скорее всего нехватка памяти

rene
Offline
Зарегистрирован: 21.01.2014

Вообще это функция, вот она:

void _SendData(byte eventType) {

  byte packHeader[5]; // массив для хранения заголовка пакета
  packHeader[0] = deviceId; // номер устройства
  Serial.print(packHeader[0], DEC);
  for (byte i = 1; i < 5; i ++){
    packHeader[i] = ptrSeqID[i - 1]; // номер пакета
    Serial.print(packHeader[i], DEC);
  }
  packHeader[5] = eventType; // тип события: 0-HeartBeat, 1-InputPipe, 2-OutputPipe
  Serial.print(packHeader[5], DEC);
 
  
  Serial.println(packHeader[5], DEC);
  Serial.println();

  for (byte i = 0; i < 6; i ++) Serial.println(packHeader[i], DEC);
  Serial.println();
  Serial.println(packHeader[5], DEC);
}

Параметр передающийся в функцию eventType, это и есть элемент с индексом 5. Может в этом дело?

kisoft
kisoft аватар
Offline
Зарегистрирован: 13.11.2012

byte packHeader[] = {1, 1, 0, 0, 0, 0};

и

byte packHeader[5];

это разного размера массивы, в этом и проблема. Во втором случае элемент с индексом 5 находится ЗА пределами массива.

 

rene
Offline
Зарегистрирован: 21.01.2014

Увеличил массив до 6, заработало, но не могли бы вы мне пояснить в чем тут фишка?

Может дело в том, что массив должен завершаться символом 0х0, а для этого требуется дополнительная ячейка массива?

Datak
Offline
Зарегистрирован: 09.10.2014

Нет, лишние нули тут ни при чём.

При объявлении массива в скобках указывается его размер, который равен шести.
Шесть ячеек, с индексами от 0 до 5 - посчитайте, если не верите. :)

rene
Offline
Зарегистрирован: 21.01.2014

Datak пишет:

Нет, лишние нули тут ни при чём.

При объявлении массива в скобках указывается его размер, который равен шести.
Шесть ячеек, с индексами от 0 до 5. Посчитайте, если не верите :)

Почему то думал, что при объявлении массива 0 учитывается, ну да ладно, спасибо!

kisoft
kisoft аватар
Offline
Зарегистрирован: 13.11.2012

Так для кого пишут статьи? http://arduino.ru/Reference/Array В верхней части экрана меню, там ссылки "Программирование", зайдите и почитайте.

В гугле много информации на эту тему. Вообще на тривиальные вещи в гугле можно описание найти легко. А потом народ обижается, что их в гугл посылают.

 

rene
Offline
Зарегистрирован: 21.01.2014

"Обратите внимания, что при создании массива типа char, необходим дополнительный элемент массива для нулевого символа"

Так вот откуда это у меня отложилось, но вы конечно правы, виноват, исправлюсь

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

Эта цитата не отсюда.

Чтобы 5-й элемент строки не выходил за ее пределы, ее надо объявлять с длиной 7.

Mr.Privet
Mr.Privet аватар
Offline
Зарегистрирован: 17.11.2015

Вообщем если у Вас в массиве 5 элементов, длинну нужно ставить 6, или не ставить совсем, последняя ячейка для закрытия массива в памяти, я все правильно понял?

В этом случае byte packHeader[] = {1, 1, 0, 0, 0, 0}; либо byte packHeader[6] = {1, 1, 0, 0, 0, 0}.

Tomasina
Tomasina аватар
Offline
Зарегистрирован: 09.03.2013

нет, неправильно.

Если в массиве 5 числовых элементов, то и массив нужно объявлять на 5, но с учетом нумерации с нуля это будет (визуально!) на единичку меньше, т.е. byte packHeader[5] - это массив на 5 числовых элементов, 5-й элемент вызывать как i=packHeader[4].

Если в массиве 5 символьных элементов, то массив нужно объявлять на одну ячейку больше, т.к. надо одну ячейку на закрытие строки, опять же с учетом нумерации с нуля это будет запись вида char packHeader[6] - массив на 5 числовых элементов, 5-й элемент вызывать как c=packHeader[4].

kisoft
kisoft аватар
Offline
Зарегистрирован: 13.11.2012

Для char массивов совершенно не обязательно добавлять один элемент под '\0', это зависит от применения. На практике есть данные, которые хранят в массиве, например char state[5] = { '0', '0', '1', '0', '1' }; Т.е. это не С-строка, а строка с фиксированной длиной. Разумеется в этом случае нельзя использовать функции типа strlen.

 

rene
Offline
Зарегистрирован: 21.01.2014

Опять!

Только что мне доказали что для 5 элементов массива надо объявлять [5], а вы говорите что отсчет идет с нуля, т.е. объявляем [4]. Дык не работает так! Где правда?

vk007
Offline
Зарегистрирован: 16.06.2015

Что же тут сложного?

Надо объявить массив на 5 элементов, так и объявляйте как _тип_ myArray[5]. Элементы массива будут иметь номера [0], [1], [2], [3] и [4] - всего 5 штук.

Если в массиве надо хранить строку, например, "mystring" (8 букв), то массив надо объявлять на 1 больше.

Т.е. в данном случае размером 9 - char myArray[9].

'm' - номер [0], 'y' - номер [1], 's' - номер [2], ....., 'g' - номер [7] и номером [8] будет символ конца строки. Итого 9.

rene
Offline
Зарегистрирован: 21.01.2014

Да, не внимательно прочитал пост 12, не правильно понял смысл. Теперь все встало на свои места. Спасибо!