Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Set bit X of an integer to bit Y of another integer without branching?

Can the copy_bit function below be simplified to something like out[out_bit] = in[in_bit]? (i.e. Not using an if statement)

template< typename T >
inline void copy_bit( T& out, const T in, const std::size_t out_bit, const std::size_t in_bit )
{
    if ( (in & (1 << in_bit)) != 0 )
    {
        out |= (1 << out_bit); // Set bit
    }
    else
    {
        out &= ~(1 << out_bit); // Clear bit
    }
}

// Set bit 4 in x to bit 11 in y
copy_bit( x, y, 4, 11 );

Update: Just to be clear, this isn't homework or an XY problem where suggesting std::bitset answers the question.

like image 240
x-x Avatar asked Aug 11 '14 05:08

x-x


2 Answers

you can do it like that like this:

//Change the bit if and only if they are not equal:
out ^= (((out >> out_bit) ^ (in >> in_bit)) & 1) << out_bit;

(Shift both values so that the required bits are in the least significant position with >>, select with & only the lower bit of the result of the ^ operation; then shift the result into position of an otherwise zero-value to ^ with the original destination. The result is the same as copying bit in_bit of in to bit out_bit of out.)

like image 146
Roee Gavirel Avatar answered Oct 21 '22 05:10

Roee Gavirel


One way to do so in one line would be to first reset the output bit to zero, and then OR it with whatever bit the in number has:

(out &= ~(1 << out_bit)) |= (((in >> in_bit) & 1) << out_bit)
like image 20
Ishamael Avatar answered Oct 21 '22 04:10

Ishamael