В стандарте C99 стандарт устанавливает следующие типы данных. В документации можно найти здесь для библиотеки stdint АВР.
uint8_t
означает, что это'ы 8-битный беззнаковый тип.uint_fast8_t
означает, что это's быстрейшим беззнаковый инт, по крайней мере 8
бит.uint_least8_t
означает, что это'ы беззнаковый инт, по крайней мере 8 бит.Я понимаю uint8_t
и что такое uint_fast8_t
( я не'т знаю, как это'ов, реализуемых на уровне регистра).
1.Можете ли вы объяснить, в чем смысл "Это'ы беззнаковый инт
не менее 8 бит на"?
2.Как uint_fast8_t " и " uint_least8_tпоможет повысить эффективность/код места, по сравнению с
uint8_t`?
uint_least8_t
самый маленький тип, который имеет по крайней мере 8 бит.
uint_fast8_t
это самый быстрый тип, который имеет по крайней мере 8 бит.
Вы можете увидеть различия, представляя экзотические архитектуры. Представьте себе 20-битной архитектурой. Его беззнаковый инт
имеет 20 бит (Единый реестр), и без знака charи 10 бит. Так как sizeof(тип int) == 2
, А типа Чара
требует дополнительной инструкции, чтобы вырезать регистров в два раза. Затем:
uint8_t
: неопределено (не 8 бит тип).uint_least8_t
: это беззнаковый тип char
, самый маленький тип, не менее 8 бит.uint_fast8_t
: это беззнаковый инт
, потому что в моей воображаемой архитектуры, полтора-регистровой переменной медленнее, чем зарегистрировать.uint8_t
означает: дайте мне беззнаковый инт ровно 8 бит.
uint_least8_t
означает: дайте мне самый маленький тип беззнаковый тип int, который имеет не менее 8 бит. Для оптимизации потребления памяти.
uint_fast8_t
означает: дайте мне беззнаковый инт не менее 8 бит. Выбрать большего размера если это сделает мою программу быстрее, из-за соображений центровки. Оптимизировать для скорости.
Также, в отличие от типов равнина инт
, подписанной версией выше stdint.ч видах гарантированно 2'формат с дополнением.
Теория идет что-то вроде:
uint8_t
должна быть ровно 8 бит, но это's не обязательно должны существовать. Так что вы должны использовать его там, где вы рассчитываете на по модулю 256 присвоение поведения* в 8-битное целое число и где вы предпочитаете составить отказ спекуляций на непонятную архитектуру.
uint_least8_t
требуется наименьший возможный беззнаковый целочисленный тип, который может хранить как минимум 8 бит. Вы бы использовать его, когда вы хотите уменьшить использование памяти такие вещи, как большие массивы.
uint_fast8_t
должна быть в "Быстрый" по-беззнаковый тип, который может хранить по крайней мере 8 бит, однако, это'ов на самом деле не гарантировано, чтобы быть быстрым при любой операции на любом процессоре. Вы бы использовать его в код обработки, который выполняет много операций на стоимость.
Практика такова, что "быстро" и "минимум" в видах арен'т использовать много.
В "минимум" в видах только действительно полезно, если вы заботитесь о переносимости, чтобы скрыть архитектур с CHAR_BIT != 8 большинство людей не'т.
Проблема с том, что "быстро" и типа, что "Быстрый" это трудно придавить. Меньший тип может означать меньшую нагрузку на системы памяти/кэша, но, используя тип, который меньше, чем родной, может потребовать дополнительных инструкций. Кроме того, которая лучше всего может меняться от версии архитектуры, но исполнители часто хотят избежать нарушения аби в таких случаях.
Глядя На некоторых популярных реализаций кажется, что определения uint_fastn_t достаточно произвольным. в glibc представляется, что определение их как минимум в "родное слово размер" из системы без учета того, что многие современные процессоры (особенно 64-битные) имеют специальную поддержку для быстрых операций на более мелких элементов, чем их родное слово размер. Для iOS, видимо, определяет их как эквивалентные типы фиксированного размера. Другие платформы могут различаться.
В общем, если эффективность туго код с крошечными чисел-это ваша цель, вы должны быть скамьи-маркировка код код на платформах с разных размеров типов, чтобы увидеть, что работает лучше.
* Обратите внимание, что к сожалению по модулю 256 поведения задание не всегда подразумевает по модулю 256 арифметики, благодаря c's в целое число поиск поощрения.
Некоторые процессоры не могут работать так же эффективно на меньшие типы данных, как на крупных. Например, дано:
uint32_t foo(uint32_t x, uint8_t y)
{
x+=y;
y+=2;
x+=y;
y+=4;
x+=y;
y+=6;
x+=y;
return x;
}
если у
были uint32_t
компилятор для ядра Cortex-м3 рука может просто создать
add r0,r0,r1,asl #2 ; x+=(y<<2)
add r0,r0,#12 ; x+=12
bx lr ; return x
но так как Y
является uint8_t
компилятор бы вместо этого создать:
add r0,r0,r1 ; x+=y
add r1,r1,#2 ; Compute y+2
and r1,r1,#255 ; y=(y+2) & 255
add r0,r0,r1 ; x+=y
add r1,r1,#4 ; Compute y+4
and r1,r1,#255 ; y=(y+4) & 255
add r0,r0,r1 ; x+=y
add r1,r1,#6 ; Compute y+6
and r1,r1,#255 ; y=(y+6) & 255
add r0,r0,r1 ; x+=y
bx lr ; return x
Назначение в "быстрой" в видах было позволить компиляторы заменить более мелкими видами, которые не мог'т быть обработаны качественно с быстрой. К сожалению, семантика и"Быстрый" в видах весьма плохо определено, что в свою очередь оставляет мутные вопросы ли выражения будет оцениваться с помощью signed или unsigned математике.
1.Можете ли вы объяснить, в чем смысл "Это'с беззнаковым целым, по крайней мере 8 бит, то"?
Это должно быть очевидно. Это означает, что он'ы беззнаковый целочисленный тип, и что он's; ширина не менее 8 бит. Фактически это означает, что он может, по крайней мере, удерживая цифры от 0 до 255, и это, безусловно, не может занимать отрицательных чисел, но он может содержать числа меньше 255.
Очевидно, вы не должны использовать любой из этих типов, если вы планируете хранить любое число вне диапазона от 0 до 255 (и вы хотите, чтобы быть портативным).
2.Как uint_fast8_t и uint_least8_t способствовать повышению эффективности кода по сравнению с uint8_t?
uint_fast8_t
должен быть быстрее, так что вы должны использовать, если ваше требование заключается в том, что код будет быстрее. `uint_least8_t с другой стороны, требует, что нет кандидата меньшего размера - так вам будет использовать, что если размер является проблемой.
И конечно, вы используете только uint8_t
, когда вы абсолютно требуют, чтобы он был ровно 8 бит. Используя uint8_t может сделать non-портативный код как
uint8_t` не обязательно должны существовать (потому что такие маленькие типа integer не существует на некоторых платформах).
В "быстрой" и целых типов определены, чтобы быть самым быстрым целочисленных, по крайней мере, количество бит необходимое (в вашем случае 8).
Платформа может определить uint_fast8_t
как uint8_t
тогда будет абсолютно никакой разницы в скорости.
Причина в том, что есть платформы, которые медленнее, когда не используете их родной длины слова.