[英]How to swap first and last nibbles in given integer [32 bits]
Suppose:认为:
No = 77
77 in binary [32 bits] : 0000 0000 0000 0000 0000 0000 0100 1101
I have to swap first and last nibble:我必须交换第一个和最后一个半字节:
i.e : 1101 0000 0000 0000 0000 0000 0100 0000
I was doing something like this:我正在做这样的事情:
no << 32 | no >> 32
Then in a loop anding it with 1 and printing.然后循环并用 1 和打印。 But it does not work out.但这行不通。
#include<stdio.h>
int main()
{
int decimalNumber;
printf("Enter your decimal number: ");
scanf("%d", &decimalNumber);
int i, j;
/* Binary conversion */
for(i=31;i>=0;i--)
{
printf("%d", (decimalNumber >> i) & 1);
}
printf("\n");
printf("After nibble swapping: \n");
/* Nibble swapping */
decimalNumber = (decimalNumber>>28) | (decimalNumber<<28);
for(i=31;i>=0;i--)
{
printf("%d",((decimalNumber>>i)&1 ? 1 : 0));
}
printf("\n");
return 0;
}
Given an unsigned integer d
and b
number of bits where b <= CHAR_BIT * sizeof(d) / 2
you obtain the result by bitwise OR
of these components:给定一个无符号的 integer d
和b
位数,其中b <= CHAR_BIT * sizeof(d) / 2
您可以通过这些组件的按位OR
运算获得结果:
Left shift the lower b
bits to the top ( sizeof (d) - (b)
is 28
bits in this case).将较低的b
位左移到顶部( sizeof (d) - (b)
在这种情况下为28
位)。 When you left shift the lower bits become 0. With example data the value is 0x8000000
.当您左移时,低位变为 0。对于示例数据,该值为0x8000000
。
The left followed by right shift clears the top b
bits, and the right followed by left shift clears the lower b
bits.左移后右移清除高b
位,右移后左移清除低b
位。 With the example data the value is 0x02345670
.对于示例数据,值为0x02345670
。 This equivalent bitwise AND
of the mask 0x0ffffff0
for a 32-bit number.这等效于 32 位数字的掩码0x0ffffff0
的按位AND
。 The shift works for any unsigned integer type irregardless of size.该班次适用于任何无符号 integer 类型,无论其大小如何。
Right shift the top b
bits to the bottom.将高位b
位右移到低位。 When you right shift the upper b
bits become zero.当您右移时,高位b
位变为零。 With the example data the value is 0x00000001
.对于示例数据,值为0x00000001
。
#include <limits.h>
#include <stdio.h>
#include <stdint.h>
#define SWAP_BITS(d, b) \
/* 1 */ (d) << CHAR_BIT * sizeof (d) - (b) |\
/* 2 */ (d) << (b) >> (b) >> (b) << (b) |\
/* 3 */ (d) >> CHAR_BIT * sizeof (d) - (b)
int main() {
uint32_t d = 0x12345678;
printf("%x\n%x\n", d, SWAP_BITS(d, 4));
}
and the outcome is:结果是:
82345671
swap first and last nibbles in given integer (32 bits)交换给定 integer(32 位)中的第一个和最后一个半字节
OP's decimalNumber = (decimalNumber>>28) | (decimalNumber<<28);
OP 的decimalNumber = (decimalNumber>>28) | (decimalNumber<<28);
decimalNumber = (decimalNumber>>28) | (decimalNumber<<28);
fails as the |
失败为|
or's the data, not replace it.或者是数据,而不是替换它。 Also shifting by 28 shifts the middle bits, which need to remain in place.同样移动 28 位会移动需要保留在原位的中间位。
Use unsigned types to not shift into or out of the sign bit.使用无符号类型不移入或移出符号位。
For a fixed sized tasks, consider using fixed sized types from #include <stdint.h>
.对于固定大小的任务,请考虑使用#include <stdint.h>
中的固定大小类型。
Print data with %X to better see what is happening.使用 %X 打印数据以更好地查看发生了什么。
uint32_t uvalue = decimalNumber;
printf("Before %lu\n", (unsigned long) uvalue); // In decimal
printf("Before 0x%lX\n", (unsigned long) uvalue); // In hexadecimal
// Get first (most significant) and last (least significant) nibble.
uint32_t first_nibble = uvalue >> (32-4);
uint32_t last_nibble = uvalue & 0xF;
// zero out the first and last nibble.
uvalue &= 0x0FFFFFF0;
// Now "or" in the replacement nibbles.
uvalue |= first_nibble;
uvalue |= last_nibble << (32-4);
printf("After 0x%lX\n", (unsigned long) uvalue);
printf("After %lu\n", (unsigned long) uvalue);
For those who like one-liners对于那些喜欢单线的人
printf("After %lu\n", (unsigned long) (
(((uint32_t) decimalNumber) & 0xF) << 28) |
((uint32_t) decimalNumber) & 0x0FFFFFF0) |
((uint32_t) decimalNumber) >> 28) |
));
Some would consider the first nibble as the least significant nibble.有些人会认为第一个半字节是最不重要的半字节。 Whatever is first or last makes little difference here as they are swapped.无论是第一个还是最后一个都没有什么区别,因为它们被交换了。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.