简体   繁体   English

如何交换给定 integer [32 位] 中的第一个和最后一个半字节

[英]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 db位数,其中b <= CHAR_BIT * sizeof(d) / 2您可以通过这些组件的按位OR运算获得结果:

  1. 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

  2. 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 类型,无论其大小如何。

  3. 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.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM