C ++ Какой лучший способ завершить этот 8-битный цикл for

Можно ли написать это для цикла короче или более элегантно, не используя uint16_t? При переполнении я достигает 0xFF.

for (uint8_t i = 0; i <= 0xFF; i++)
{
// do something
if (i == 0xFF)
break;
}

4

Решение

Чтобы охватить весь диапазон, нам просто нужно выполнить тест после тела цикла, так что здесь удобно использовать do … while:

uint8_t i = 0;
do {
...
} while (i++ < 0xFF);
7

Другие решения

Поскольку переполнение для чисел без знака хорошо определено, этот цикл может сделать это:

uint8_t i = 0;
do {
// use i here
i++;
} while (i);

я переполняется (становится 0) на 256-й итерации и время останавливается, потому что условие ложно.

Примечание: этот трюк того стоит, только если вы на <32-битная платформа. На> = 32-битных платформах есть большая вероятность, что этот трюк будет преобразован в цикл, который использует> = 32-битный счетчик.

С другой стороны, на 8-битных платформах я думаю, что это самый эффективный и самый маленький цикл с 256 итерациями.

3

Не самый короткий, но самый крутой способ сделать это — объявить массив со всеми возможными значениями uint8_t и перебрать его.

#include <iostream>
#include <cstdint>
#include <limits>

namespace detail {
template<typename int_t, int_t cnt, bool not_done, int_t... rest>
struct range_impl {
static constexpr auto& value = range_impl<int_t, cnt - 1,
(cnt - 1) != std::numeric_limits<int_t>::min(), cnt, rest...>::value;
};

template<typename int_t, int_t cnt, int_t... rest>
struct range_impl<int_t, cnt, false, rest...> {
static constexpr int_t value[] = { cnt, rest... };
};

template<typename int_t, int_t cnt, int_t... rest>
constexpr int_t range_impl<int_t, cnt, false, rest...>::value[];
} // detail

template<typename int_t>
struct range : public detail::range_impl<int_t, std::numeric_limits<int_t>::max(), true> {};

int main(int argc, char** argv) {
for(uint8_t i: range<uint8_t>::value) {
std::cout <<  (int) i << std::endl;
}

for(int8_t i: range<int8_t>::value) {
std::cout <<  (int) i << std::endl;
}
}

range Структура генерирует массив во время компиляции. Этот код можно использовать для любого целочисленного типа.

1
По вопросам рекламы [email protected]