如何用位运算实现4位二进制数到指定8位二进制数的转换?
Hey there! Let's unpack this conversion problem step by step—your mapping has a really clear pattern once you look closely.
First, Identify the Pattern
Looking at your input-output pairs, each bit in the 4-bit input expands to two identical bits in the 8-bit output. Let's label the 4-bit input as b3 b2 b1 b0 (where b3 is the most significant bit, b0 the least):
- If
b3 = 1, the top two bits of the output become11(e.g.,1000→11000000) - If
b2 = 1, the next pair of bits become11(e.g.,0100→00110000) - If
b1 = 1, the middle pair become11(e.g.,0010→00001100) - If
b0 = 1, the bottom two bits become11(e.g.,0001→00000011)
When multiple input bits are 1, their corresponding output bit pairs are all set to 11 (e.g., 0011 combines b1 and b0 → 00001111).
The Bitwise Expression
Based on this pattern, here's a concise, readable bitwise expression to implement the conversion (let x be your 4-bit input value):
uint8_t result = (((x >> 3) & 1) * 0xC0) | (((x >> 2) & 1) * 0x30) | (((x >> 1) & 1) * 0x0C) | ((x & 1) * 0x03);
What Each Part Does
0xC0=11000000(mask for the top two output bits)0x30=00110000(mask for the second output bit pair)0x0C=00001100(mask for the middle output bit pair)0x03=00000011(mask for the bottom two output bits)
For each bit in the input:
(x >> n) & 1checks if the nth bit is set (returns 1 if yes, 0 otherwise)- Multiply by the corresponding mask to set the two bits in the output
- Use bitwise OR (
|) to combine all the masked values into the final 8-bit result
Let's Test It
Let's verify with a couple of your examples to make sure it works:
- Input
0101(decimal 5):((5 >> 3) & 1) = 0,((5 >> 2) & 1) = 1,((5 >> 1) & 1) = 0,(5 & 1) = 1- Result:
0*0xC0 + 1*0x30 + 0*0x0C + 1*0x03 = 0x33→00110011(matches your target!)
- Input
1011(decimal 11):((11 >> 3) & 1) = 1,((11 >> 2) & 1) = 0,((11 >> 1) & 1) = 1,(11 & 1) = 1- Result:
1*0xC0 + 0*0x30 + 1*0x0C + 1*0x03 = 0xCF→11001111(perfect!)
If you prefer a more "pure" bit-shift version without multiplication, here's an alternative:
uint8_t result = (((x >> 3) & 1) << 7) | (((x >> 3) & 1) << 6) | (((x >> 2) & 1) << 5) | (((x >> 2) & 1) << 4) | (((x >> 1) & 1) << 3) | (((x >> 1) & 1) << 2) | ((x & 1) << 1) | ((x & 1) << 0);
This does the same thing—each input bit is shifted to both positions in its target output pair, then combined with OR.
内容的提问来源于stack exchange,提问作者NguyenTam

