Интересная проблема, о которой я размышлял последние несколько дней, - это копирование целочисленных битов в другое целое число в заданной позиции в целевом целое. Так, например, с учетом целевого целого числа 0xdeadbeef
и исходного целого числа 0xabcd
, идея заключалась бы в получении результата 0xabcdbeef
(с заданной позицией 16 бит) или 0xdeabcdef
(с учетом позиции адресата из 8 бит).
При произвольном ограничении избегания условных или петель (позволяя мне использовать только математические/побитовые операции), я разработал следующую функцию (С++)
int setbits(int destination, int source, int at, int numbits)
{
int ones = ((1<<(numbits))-1)<<at;
return (ones|destination)^((~source<<at)&ones);
}
где at
- это место, где исходные биты должны быть скопированы в номер назначения (0-31), а numbits
- количество бит, копируемых из source
(1-32). Насколько я могу судить, этот алгоритм работает для всех значений, за исключением at
= 0 и numbits
= 32 (случай, когда целое целые назначения переписываются исходным целым) из-за того, что 1 < < lt; 32 приводит к 1 (так как сдвиг обертывается вокруг) в противоположность 0.
Мои вопросы:
- Как это обычно делается? Существуют ли какие-либо особенно заметные алгоритмы (замечательно, я спрашиваю, есть ли особенно эффективные трюки, которые можно использовать для этого)?
- Работает ли мой алгоритм так же хорошо, как я думаю (он работает для всех значений, кроме = 0 и numbits = 32)?
- В связи с 1), есть ли способ сделать это только с использованием математических/побитовых операторов? Алгоритм для всех значений тривиален с использованием условий или циклов, поэтому я не заинтересован в этом.
Дизайн алгоритма, как правило, является слабым местом для меня, поэтому я не знаю, действительно ли мой алгоритм "так же хорош, как он получается", только при использовании математических/побитовых операций. Благодаря