В ИСО / МЭК 9899: 2018 (С18) указано в 7.20.1.3:
7.20.1.3 Самые быстрые целочисленные типы минимальной ширины
1 Каждый из следующих типов обозначает целочисленный тип, который обычно является самым быстрым ( 268) для работы среди всех целочисленных типов, которые имеют по меньшей мере указанную ширину.
2 Имя typedef
int_fastN_t
обозначает самый быстрый целочисленный тип со знаком с шириной не менее N. Имя typedefuint_fastN_t
обозначает самый быстрый целочисленный тип без знака с шириной не менее N.3 Требуются следующие типы:
int_fast8_t
,int_fast16_t
,int_fast32_t
,int_fast64_t
,uint_fast8_t
,uint_fast16_t
,uint_fast32_t
,uint_fast64_t
Все остальные типы этой формы являются необязательными.
268) Назначенный тип не гарантируется быть самым быстрым для всех целей; если реализация не имеет четких оснований для выбора одного типа над другим, она просто выберет некоторый целочисленный тип, удовлетворяющий требованиям подписи и ширины.
Но не указано, почему эти «быстрые» целочисленные типы быстрее.
- Почему эти быстрые целочисленные типы быстрее, чем другие целочисленные типы?
Я пометил вопрос с C ++, потому что быстрые целочисленные типы также доступны на C ++ 17 в заголовочном файле cstdint
. К сожалению, в ISO / IEC 14882: 2017 (C ++ 17) нет такого раздела об их объяснении; Я реализовал этот раздел иначе в теле вопроса.
Информация: в C они объявлены в заголовочном файле stdint.h
.
typedef
утверждениями. Как правило , это делается на уровне стандартной библиотеки. Разумеется, C стандарт не накладывает реальное ограничение на то , что ониtypedef
- значит , например , типичная реализация сделать из на 32-битную системе, но гипотетический компилятор может , например , реализовать присущий тип и обещает сделать некоторые фантазии Оптимизация для выбора самого быстрого типа машины в каждом конкретном случае для переменных этого типа, а затем библиотека может просто к этому.int_fast32_t
typedef
int
__int_fast
typedef
Ответы:
Представьте себе процессор, который выполняет только 64-битные арифметические операции. Теперь представьте, как бы вы реализовали 8-битное дополнение без знака на таком процессоре. Чтобы получить правильный результат, потребуется несколько операций. На таком процессоре 64-битные операции выполняются быстрее, чем операции с другими целочисленными значениями. В этой ситуации все они
Xint_fastY_t
могут быть псевдонимами 64-битного типа.Если ЦП поддерживает быстрые операции для узких целочисленных типов и, следовательно, более широкий тип не быстрее, чем более узкий, тогда
Xint_fastY_t
не будет псевдоним более широкого типа, чем это необходимо для представления всех битов Y.Из любопытства я проверил размеры для конкретной реализации (GNU, Linux) на некоторых архитектурах. Они не одинаковы для всех реализаций на одной архитектуре:
Обратите внимание, что хотя операции с большими типами могут выполняться быстрее, такие типы также занимают больше места в кэше, и, следовательно, их использование не обязательно приводит к повышению производительности. Кроме того, нельзя всегда полагать, что реализация сделала правильный выбор в первую очередь. Как всегда, измерения необходимы для достижения оптимальных результатов.
Скриншот таблицы, для пользователей Android:
(Android не имеет черчения символов в моно шрифте - ссылка )
источник
Они не, по крайней мере, не надежно.
Быстрые типы - это просто определения типов для обычных типов, однако их определение зависит от реализации. Они должны быть как минимум требуемого размера, но они могут быть больше.
Это правда, что на некоторых архитектурах некоторые целочисленные типы имеют лучшую производительность, чем другие. Например, ранние реализации ARM имели инструкции доступа к памяти для 32-битных слов и для байтов без знака, но у них не было инструкций для полуслов или байтов со знаком. Команды из полуслов и со знаком байтов были добавлены позже, но они по-прежнему имеют менее гибкие параметры адресации, поскольку их необходимо было вставить в свободное пространство кодирования. Кроме того, все действительные инструкции по обработке данных в ARM работают со словами, поэтому в некоторых случаях может потребоваться маскировать меньшие значения после вычисления, чтобы получить правильные результаты.
Тем не менее, существует также конкурирующая проблема давления в кэше, даже если для загрузки / хранения / обработки меньшего значения требуется больше инструкций. Меньшее значение может все еще работать лучше, если оно уменьшает количество пропусков кэша.
Определения типов на многих распространенных платформах, похоже, еще не продуманы. В частности, современные 64-битные платформы, как правило, имеют хорошую поддержку 32-битных целых чисел, однако «быстрые» типы часто излишне 64-битные на этих платформах.
Кроме того, типы в C становятся частью ABI платформы. Таким образом, даже если поставщик платформы обнаружит, что он сделал глупый выбор, трудно изменить этот тупой выбор позже.
Игнорируйте «быстрые» типы. Если вы действительно обеспокоены целочисленной производительностью, сравните ваш код со всеми доступными размерами.
источник
Быстрые типы не быстрее, чем все другие целочисленные типы - они фактически идентичны некоторому «нормальному» целочисленному типу (они просто псевдонимы для этого типа) - какой бы тип не оказался самым быстрым для хранения значения по крайней мере, так много битов.
Это просто зависит от платформы, для какого целого типа каждый быстрый тип является псевдонимом.
источник