Форум программистов, компьютерный форум, киберфорум
Микроконтроллеры ARM, Cortex, STM32
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.55/11: Рейтинг темы: голосов - 11, средняя оценка - 4.55
4 / 4 / 0
Регистрация: 12.11.2018
Сообщений: 511

Переполнение целочисленной переменной

22.10.2021, 15:28. Показов 2475. Ответов 16

Студворк — интернет-сервис помощи студентам
В процессе работы кода происходит следующее действие:
C
1
StackBuff[b][a] = StackBuff[b][a]/FilterValue[a];
где
StackBuff объявлен как uint16_t, а FilterValue как float. Т.е. целочисленные элементы массива делятся на некоторые коэффициенты, значения которых находятся в районе 1 (примерно от 0.8 - 1.2). В процессе работы, чисто теоритически, может возникнуть ситуация, при которой произойдет переполнение элементов массива StackBuff. Вопрос: как можно отследить данное переполнение?
0
Лучшие ответы (1)
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
22.10.2021, 15:28
Ответы с готовыми решениями:

Заменить в целочисленной переменной х бит старшими инвертированными битами целочисленной переменной
7. Заменить в целочисленной переменной х п бит, начиная с позиции р, п старшими инвертированными битами целочисленной переменной у.

Переполнение переменной (не совсем)
Проблема возникла с переполнением переменной. Я поменял ее тип на Double и расчеты пошли нормально но теперь итоговый результат выводиться...

Проверка на переполнение переменной
Помогите пожалуйста сделать проверку на переполнение переменной using System; namespace ConsoleApplication3 { class...

16
Эксперт CЭксперт С++
 Аватар для liv
5120 / 4574 / 855
Регистрация: 07.10.2015
Сообщений: 9,462
22.10.2021, 16:13
DmitryDDDD, как вариант, сделать StackBuff uint32_t. После деления проверять, помещается ли значение в uint_16. Если нет, принять меры.
1
Почетный модератор
 Аватар для Humanoid
11557 / 4352 / 452
Регистрация: 12.06.2008
Сообщений: 12,454
22.10.2021, 22:12
Лучший ответ Сообщение было отмечено DmitryDDDD как решение

Решение

Если float окажется совсем маленький, то и uint32_t переполнится. Мне кажется, проще всего использовать промежуточную переменную float:
C
1
2
3
4
5
float tmp = StackBuff[b][a] / FilterValue[a];
if (tmp > (uint16_t)-1) {
  // какие-то действия при переполнении... например, tmp = (uint16_t)-1;
}
StackBuff[b][a] = (uint16_t)tmp;
Или можно вначале проверять, переполнится ли результат... ведь нам надо получить "a / b <= 0xffff", значит a <= b * 0xffff
C
1
2
3
4
5
if (((uint16_t)-1 * FilterValue[a]) < StackBuff[b][a]) {
// переполнится
} else {
  StackBuff[b][a] = StackBuff[b][a]/FilterValue[a]
}
Не уверен, но думаю, что второй вариант будет медленнее, т.к. тут будет выполняться, помимо деления, ещё и умножение.
1
210 / 163 / 36
Регистрация: 15.11.2012
Сообщений: 788
22.10.2021, 22:42
Цитата Сообщение от DmitryDDDD Посмотреть сообщение
как можно отследить данное переполнение?
C
1
2
3
4
int t;
...
StackBuff[b][a] = t = StackBuff[b][a]/FilterValue[a];
if (t >= 65536) ...
указанный способ едва ли приведет к каким либо дополнительным расходам по вычислениям. Главное - не писать (t = StackBuff[b][a] = ...), надо именно (StackBuff[b][a] = t = ...)

Понял что написал то что уже написано...
1
4 / 4 / 0
Регистрация: 12.11.2018
Сообщений: 511
23.10.2021, 07:32  [ТС]
liv, Humanoid, alexey6689,
Всем спасибо за ответы, наверно, в данной ситуации будет лучшим решением использовать дополнительную переменную. Попробую реализовать код, который предложил Humanoid,
Цитата Сообщение от Humanoid Посмотреть сообщение
float tmp = StackBuff[b][a] / FilterValue[a];
if (tmp > (uint16_t)-1) {
  // какие-то действия при переполнении... например, tmp = (uint16_t)-1;
}
StackBuff[b][a] = (uint16_t)tmp;
Если я все правильно понял и (uint16_t)-1) это 0xFFFF, то это то, что мне надо
0
Почетный модератор
 Аватар для Humanoid
11557 / 4352 / 452
Регистрация: 12.06.2008
Сообщений: 12,454
23.10.2021, 10:46
Цитата Сообщение от DmitryDDDD Посмотреть сообщение
Если я все правильно понял и (uint16_t)-1) это 0xFFFF
Да, всё верно.
0
 Аватар для COKPOWEHEU
4083 / 2681 / 432
Регистрация: 09.09.2017
Сообщений: 11,921
24.10.2021, 10:05
А может просто до умножения проверить на (0xFFFF/1.2 ≈ 54600). Если речь о переполнении, то есть заведомо ошибочной ситуации, вряд ли так уж нужна точность:
C
1
2
3
4
5
if(StackBuff[b][a] < 54600 ){ //54600 - "максимальное" число, которое можно умножить на 1.2 без переполнения
  StackBuff[b][a] = StackBuff[b][a] / FilterValue[a];
}else{
  //error
}
0
4 / 4 / 0
Регистрация: 12.11.2018
Сообщений: 511
24.10.2021, 11:18  [ТС]
COKPOWEHEU, ну диапозон 0.8 - 1.2 это ожидаемые границы, что там будет, когда будет не стандартная ситуация или какие-то вылеты точно сказать нельзя, да и при ситуации когда StackBuff[b][a] надо будет умножить на 1.2, а StackBuff[b][a+1] надо умножить на 0.8, делать проверку всех чисел на < (0xFFFF/1.2 ≈ 54600) несовсем рационально
0
 Аватар для COKPOWEHEU
4083 / 2681 / 432
Регистрация: 09.09.2017
Сообщений: 11,921
24.10.2021, 12:15
Цитата Сообщение от DmitryDDDD Посмотреть сообщение
ну диапозон 0.8 - 1.2 это ожидаемые границы, что там будет, когда будет не стандартная ситуация
Ну так задайте верхнюю границу и делите на нее.
Цитата Сообщение от DmitryDDDD Посмотреть сообщение
при ситуации когда StackBuff[b][a] надо будет умножить на 1.2, а StackBuff[b][a+1] надо умножить на 0.8, делать проверку всех чисел на < (0xFFFF/1.2 ≈ 54600) несовсем рационально
Сравнение с константой гораздо более дешевая операция, чем использование чисел большей разрядности, которые точно так же требуют сравнения.
Или вопрос в том, что рабочий диапазон оказался слишком близко к критическим значениям? Так это вопрос правильного конструирования архитектуры и надежности приложения.
Цитата Сообщение от DmitryDDDD Посмотреть сообщение
не стандартная ситуация или какие-то вылеты
А как вы собирались обрабатывать нештатные ситуации вроде переполнения? Вот так же и эту обрабатывайте.
0
4 / 4 / 0
Регистрация: 12.11.2018
Сообщений: 511
24.10.2021, 19:00  [ТС]
COKPOWEHEU, не, может я не доконца объяснил, может Вы не совсем проавильно понимаете задачу, смотрите:
есть набор 16 битных чисел и набор коэффициентов, на которые надо их умножать.
Числа лежат в диапазоне от 0 до 65535 (16 бит), коэффициенты условно от 0.8 до 1.2 (коэффициенты рассчитываются на основании измерений), но если брать с запасом то, пусть будет от 0.5 до 1.8. Т.е. все 16 битные числа массива я должен фильтровать по величине 65536/1.8 = 36408, все что больше этого числа не проходит проверку, но это будет не правилнь. Ибо ситуация, что надо будет умножать 36408 на 1.8 вероятна, но не типична, гораздо более популярной ситуацией может оказаться что числа близкие к 65000 надо будет умножить на 0.95-1.05. Да, возможно это более ресурсозатратно, но такой расчет выполняется после завершения всех измерений микроконтроллером поэтому лишние миллисекунды, потраченные на это, не столь существенны
0
 Аватар для COKPOWEHEU
4083 / 2681 / 432
Регистрация: 09.09.2017
Сообщений: 11,921
24.10.2021, 20:15
Откуда же эти числа берутся, что так точно совпадают с диапазоном uint16_t? Что-то мне не нравится, что нет никакого запаса.
Цитата Сообщение от DmitryDDDD Посмотреть сообщение
FilterValue как float
Цитата Сообщение от DmitryDDDD Посмотреть сообщение
такой расчет выполняется после завершения всех измерений микроконтроллером
float на контроллере? Обычно это не лучшая идея. Возможно, стоит заменить на вычисления с фиксированной точкой.
0
Модератор
Эксперт по электронике
8981 / 6748 / 921
Регистрация: 14.02.2011
Сообщений: 23,870
24.10.2021, 20:21
Цитата Сообщение от COKPOWEHEU Посмотреть сообщение
float на контроллере?
а что так пугает
у 401 и выше уже встроен блок для работы с числами с плавающей точкой
0
 Аватар для COKPOWEHEU
4083 / 2681 / 432
Регистрация: 09.09.2017
Сообщений: 11,921
24.10.2021, 22:49
У меня пока не возникало задач под такие мощные камни. Насколько там float медленнее фиксированной точки?
0
Модератор
Эксперт по электронике
8981 / 6748 / 921
Регистрация: 14.02.2011
Сообщений: 23,870
24.10.2021, 23:19
Цитата Сообщение от COKPOWEHEU Посмотреть сообщение
Насколько там float медленнее фиксированной точки?
не замерял, не могу сказать
вот статья http://microsin.net/programmin... -unit.html
0
 Аватар для COKPOWEHEU
4083 / 2681 / 432
Регистрация: 09.09.2017
Сообщений: 11,921
25.10.2021, 01:34
И что мне делать с этим переводом если задач под соответствующие контроллеры как не было, так и нет?
Впрочем, таблицу с таймингами я там нашел: умножение за 1 такт, деление за 14 тактов, сложение за 1 такт, преобразование в/из целые за 1 такт. То есть весьма быстро, хотя лишнее время на конвертацию, конечно, уйдет.
0
Модератор
Эксперт по электронике
8981 / 6748 / 921
Регистрация: 14.02.2011
Сообщений: 23,870
25.10.2021, 01:49
Цитата Сообщение от COKPOWEHEU Посмотреть сообщение
если задач под соответствующие контроллеры как не было, так и нет?
будут
0
 Аватар для COKPOWEHEU
4083 / 2681 / 432
Регистрация: 09.09.2017
Сообщений: 11,921
25.10.2021, 10:19
Вот когда будут, тогда и буду изучать
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
25.10.2021, 10:19
Помогаю со студенческими работами здесь

Как вызвать переполнение переменной?
Всем привет, не могу додуматься как специально переполнить переменную, к примеру типа char?

Как отследить переполнение переменной?
Всем привет. Возможно ли отследить переполнение переменной?

Переполнение переменной примитивного целочисленного типа
Экспериментирую в intellij idea!!!! Почему вот так: short a = (32767 + 1) - не компилится вот так short a = (short) (32767 + 1)...

Переполнение при обращении к переменной Char
Делаю все по Подбельскому, но для своей программы, ничего не получается. Собственно сам код: #include &lt;stdlib.h&gt; ...

Проверка на переполнение переменной вещественного типа
Есть ли в делфи функция/директива компилятору позволяющая отслеживать переполнение переменной вещественного типа?


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
17
Ответ Создать тему
Новые блоги и статьи
SDL3 для Web (WebAssembly): Реализация движения на Box2D v3 - трение и коллизии с повёрнутыми стенами
8Observer8 20.02.2026
Содержание блога Box2D позволяет легко создать главного героя, который не проходит сквозь стены и перемещается с заданным трением о препятствия, которые можно располагать под углом, как верхнее. . .
Конвертировать закладки radiotray-ng в m3u-плейлист
damix 19.02.2026
Это можно сделать скриптом для PowerShell. Использование . \СonvertRadiotrayToM3U. ps1 <path_to_bookmarks. json> Рядом с файлом bookmarks. json появится файл bookmarks. m3u с результатом. # Check if. . .
Семь CDC на одном интерфейсе: 5 U[S]ARTов, 1 CAN и 1 SSI
Eddy_Em 18.02.2026
Постепенно допиливаю свою "многоинтерфейсную плату". Выглядит вот так: https:/ / www. cyberforum. ru/ blog_attachment. php?attachmentid=11617&stc=1&d=1771445347 Основана на STM32F303RBT6. На борту пять. . .
Камера Toupcam IUA500KMA
Eddy_Em 12.02.2026
Т. к. у всяких "хикроботов" слишком уж мелкий пиксель, для подсмотра в ESPriF они вообще плохо годятся: уже 14 величину можно рассмотреть еле-еле лишь на экспозициях под 3 секунды (а то и больше),. . .
И ясному Солнцу
zbw 12.02.2026
И ясному Солнцу, и светлой Луне. В мире покоя нет и люди не могут жить в тишине. А жить им немного лет.
«Знание-Сила»
zbw 12.02.2026
«Знание-Сила» «Время-Деньги» «Деньги -Пуля»
SDL3 для Web (WebAssembly): Подключение Box2D v3, физика и отрисовка коллайдеров
8Observer8 12.02.2026
Содержание блога Box2D - это библиотека для 2D физики для анимаций и игр. С её помощью можно определять были ли коллизии между конкретными объектами и вызывать обработчики событий столкновения. . . .
SDL3 для Web (WebAssembly): Загрузка PNG с прозрачным фоном с помощью SDL_LoadPNG (без SDL3_image)
8Observer8 11.02.2026
Содержание блога Библиотека SDL3 содержит встроенные инструменты для базовой работы с изображениями - без использования библиотеки SDL3_image. Пошагово создадим проект для загрузки изображения. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru