Каково значение использования определенного числового типа над другим
Каково значение памяти для хранения целого числа как определенного числового типа (uint8, int16, uint32, int64 и т. Д.)? Я знаю диапазон целых чисел, который может принимать каждый из типов, но есть ли какая-то эффективность памяти, которую можно достичь с помощью соответствующего типа?
Например, в Golang "кажется" более эффективным хранить чей-то возраст как uint8, а не как единицу измерения (что эквивалентно uint32 или uint64 в соответствии с его спецификацией https://golang.org/ref/spec)
2 ответа
Целые числа фиксированного размера
Целые числа фиксированного размера требуют точного объема памяти. Используя меньший целочисленный тип "здесь и там" для отдельных переменных, вы получите только небольшой объем памяти, если таковой имеется. Также при использовании в качестве типов структурных полей вы снова можете ничего не получить из-за неявных заполнений.
Увеличение памяти может быть заметным и значительным, когда вы используете целые числа фиксированного размера в качестве типа элемента (больших) срезов или массивов.
Другая (возможно, более важная) причина использования целых чисел фиксированного размера может заключаться в сообщении того, что вы храните в них. Вы могли бы также использовать int32
или же int64
Тип для хранения байтов, но, будучи очевидной тратой, они не передают действительный диапазон хранимых в них данных.
Еще один момент - это эффективность. Вы всегда можете использовать int64
вместо других целочисленных типов со знаком, но на некоторых архитектурах, выполняющих операции над int64
может потребоваться несколько операций с регистрами и, следовательно, значительно медленнее. Так же rune
тип (псевдоним для int32
) четко сообщает, что вы намерены использовать его для кодовых точек Юникода.
Другой момент - последовательность. Если вы используете int32
чтобы моделировать что-то в одном месте, вы должны придерживаться этого и везде использовать один и тот же тип. Это более важно в Go, чем в других языках, потому что система типов Go является строгой (более строгой, чем в большинстве других языков), то есть если у вас есть значение типа int32
Вы не можете присвоить его переменной int64
тип и наоборот без явного преобразования.
int
против целых чисел фиксированного размера
Типы int
а также uint
не фиксированные размеры, но в соответствии со спецификацией: числовые типы:
uint either 32 or 64 bits int same size as uint
Когда вы используете int
компилятор может создавать более оптимизированный код, ориентируясь на разные архитектуры. Обычно int
32-битный для 32-битных архитектур и 64-битный для 64-битных архитектур. Это означает, что размер int
будет соответствовать размеру регистра целевой архитектуры, поэтому целочисленные операции могут быть эффективно выполнены с помощью операций с одним регистром. Если вы используете int64
например, это может потребовать выполнения нескольких (регистровых) операций для выполнения одной целочисленной операции в 32-битной архитектуре.
Мне нравится думать о int
являющийся целочисленным типом, который используется для описания и передачи определенных частей или компонентов структур данных времени выполнения Go наилучшим образом. Например, чтобы индексировать массивы или фрагменты, или описать их размеры, int
является "естественным" типом для использования.
Встроенные функции
len
а такжеcap
принимать аргументы разных типов и возвращать результат типаint
, Реализация гарантирует, что результат всегда вписывается вint
, Например, индексирование срезов или массива, или для описания их длины и емкости,int
"естественный" тип, рекомендуемый или применяемый.
При использовании for range
оператор с хотя бы одной итерационной переменной для массивов, срезов или string
значения, переменная итерации ("индекс") будет иметь тип int
,
Также обратите внимание, что Роб Пайк представил предложение для Go 2, чтобы изменить int
с произвольной точностью. предложение: spec: изменить int на произвольную точность
1) Целые числа фиксированного размера можно использовать для уменьшения памяти, используемой вашим приложением. Например, в 3D-приложении может иметь смысл использовать float32
скорее, чем float64
потому что видеокарта хочет float32
в любом случае и использовать uint16
скорее, чем uint32
для рисования индексов, например.
Тем не менее, для отдельных переменных это не имеет значения, только если у вас есть большое количество значений и вы можете обменять точность на память.
2) При записи на диск, например, используя кодировку / двоичный пакет, вы не можете использовать int
или же uint
потому что их размер меняется между операционными системами. Вы должны использовать значения известного размера, чтобы сделать формат файла однозначным.
3) При взаимодействии с API операционной системы часто требуется использовать переменные фиксированного размера. Например, Windows API является 32-битным API, что означает, что при загрузке Windows DLL вам часто нужно использовать 32-битные целые числа без знака для флагов и т. Д.