Как выполнить побитовое округление до четных чисел, если нечетное? - PullRequest
1 голос
/ 17 июня 2019

Как выполнить только побитовое (сдвиги, и, или, xor ..) округление до четных чисел, если число нечетное (также для отрицательных чисел)?

Пример:

  • Вход: 3;Выход: 4
  • Вход: 4;Выход: 4
  • Вход: 5;Выход: 6
  • Вход: 6;Выход: 6
  • Вход: -14;Выход: -14
  • Вход: -15;Вывод: -14

Что я пробовал: пока это работает, но кажется, что это несколько избыточно?

(((n + 1) >> 1) << 1)

Есть ли более короткое решение?

1 Ответ

1 голос
/ 19 июля 2019

Решение состоит в том, чтобы добавить младший значащий бит к числу:

n+(n&1)

Если n является четным, его младший бит равен 0, а число остается неизменным, как и ожидалось.
Если n нечетно, его младший бит равен 1, а n будет изменено на четное число непосредственно над ним.

Это основано на арифметических операциях и будет работать как для положительных, так и для отрицательных чисел.

Это даже не полагается на факт, что числа закодированы в дополнении до двух.Единственное реальное предположение состоит в том, что четные числа имеют LSB в 0, а нечетные числа - LSB в 1. Если n кодируется необычным образом, этот метод все равно должен работать при условии, что это предположение проверено.Например, с числами, закодированными в знак-абсолютное значение, или с избыточным кодом (с избыточным четным).

Ваш метод, хотя и правильный на большинстве компьютеров, реализует ((n + 1) ÷ 2) × 2средства правой и левой смен.Но стандарты C или C ++ оставляют (на данный момент) реализацию, зависящую от значения сдвига вправо на целых числах со знаком, и ваш код может разбиваться на отрицательные числа на некоторых необычных архитектурах / компиляторах.

...