如何在C

时间:2018-11-19 03:16:45

标签: c binary bit-manipulation

我不知道问题是否对,但是。

例如,十进制的25441,二进制为110001101100001。如何将其拆分为两个8位的“ 1100011”和“ 01100001”(即“ 99”和“ 97”)。但是,我只能考虑使用位操作将其移位>> 8,而我无法完成“ 97”的其余操作。这是我的功能,它不是一个很好的功能,但我希望它能对您有所帮助:

void reversecode(int input[], char result[]) {  //input is 25441
int i;
for (i = 0; i < 1; i++) {  
    result[i] = input[i] >> 8;                  // shift by 8 bit
    printf("%i", result[i]);                    //to print result
}
}

我当时正在考虑使用struct,但是我不知道如何启动它。我是C语言的初学者,为我的作风不好而感到抱歉。在此先谢谢你。

2 个答案:

答案 0 :(得分:0)

您可以使用位屏蔽概念。
像这样,

uint16_t val = 0xABCD;
uint8_t vr  = (uint8_t) (val & 0x00FF);

或者这也可以通过简单的显式类型转换来完成,因为8位整数仅携带16位值中的LBS 8位,并丢弃其余的MSB 8位(默认情况下,当分配更大的值时)。这些都是在移位后完成的。

答案 1 :(得分:0)

仅通过掩盖位input[i] & 0xFF屏蔽掉LSB。

您发布的代码input[i] >> 8在此之前给出了下一个字节。但是,如果int是32位,它也会给出碰巧存储在最高有效字节中的任何内容。所以再次需要掩盖(input[i] >> 8) & 0xFF

还要避免对诸如int之类的有符号类型进行位移位,因为如果它们具有负值,则会调用指定不正确的行为,从而导致错误。

掩盖int的各个字节的正确方法是:

// 16 bit system  
uint8_t bytes [sizeof(int)] = 
{
  ((uint16_t)i >> 0) & 0xFF,  // shift by 0 not needed, of course, just stylistic
  ((uint16_t)i >> 8) & 0xFF,
};

// 32 bit system  
uint8_t bytes [sizeof(int)] = 
{
  ((uint32_t)i >>  0) & 0xFF,
  ((uint32_t)i >>  8) & 0xFF,
  ((uint32_t)i >> 16) & 0xFF,
  ((uint32_t)i >> 24) & 0xFF,
};

这会将LSB放置在此数组的索引0处,类似于内存中的Little Endian表示形式。但是请注意,实际的移位是独立于字节序的,而且速度很快,因此这是一种更好的方法。

基于并集或指针算法的解决方案取决于字节序,并且通常存在错误(违反指针别名),因此应避免使用它们,因为使用它们没有任何好处。