Ответ 1
Это выглядит странно, но дает правильный ответ:
(4 - (string_length % 4)) % 4
Скажем, у меня есть набор данных (например: строки), которые должны быть сохранены в двоичном файле, дополненном так, чтобы каждая строка была, скажем, выровнена на 4 байта.
Итак, если у меня есть строка длиной 11, она будет заполнена до 12 (с нулевыми байтами).
Если у меня есть строка длиной 24, то никакое дополнение не требуется.
Если моя строка имеет длину 6, она будет дополняться 8 байтами.
Как вычислить количество отступов, требуемое в одном выражении?
Я пробовал 4 - (string_length % 4)
, но он терпит неудачу, когда моя длина строки кратна 4.
Это выглядит странно, но дает правильный ответ:
(4 - (string_length % 4)) % 4
Существует более быстрый способ вычисления отступов, если выравнивание равно двум (2,4,8,...). Следующие пробеги, потому что двоичные и аналогичны% для степеней двух: %(2^x)
и &(2^x-1)
делают то же самое для положительных чисел. Внимание: и будет удалять бит знака и поэтому всегда возвращает положительный результат по модулю.
Итак, (4 - (string_length & 3)) & 3
будет делать то же самое, что и (4 - (string_length % 4)) % 4
. Используя положительное свойство modulo, это можно упростить до
(-string_length) & 3
!
Если вы хотите добавить этот результат к размеру, вы можете даже сделать больше оптимизаций:
padded_length = (string_length + 3) & ~3
Семантически это "округляет" число до размера прокладки 4.
public static final int getByteAlignedIndex(final int pVariableDataIndex, final int pVariableDataLength, final int pByteAlignment) {
return pVariableDataIndex + (pVariableDataLength & 0xFFFFFFFC) + ((((pVariableDataLength & 0b1)|((pVariableDataLength & 0b10) >> 1))) << 2);
}