使用按位运算符从32位整数检索字节

时间:2012-04-12 22:19:33

标签: c

这是问题,我现在有什么问题,我只是不明白这是怎么回事......

  

getByte - 从字x提取字节n从0(LSB)到的字节数   3(MSB)示例:getByte(0x12345678,1)= 0x56法律操作:! 〜&   ^ | +<< >>最高操作:6评级:2

int getByte(int x, int n) {
  return ((x << (24 - 8 * n)) >> (8 * n));
}

3 个答案:

答案 0 :(得分:11)

你的移位没有任何意义 - 首先,你向左移动(24 - 8n)位,然后向右移动8n位。为什么?而且,这是错的。如果n为0,则将x向左移位24位并返回该值。试试笔和纸,看看这是完全错误的。

正确的做法是:

int getByte(int x, int n) {
  return (x >> 8*n) & 0xFF;
}

答案 1 :(得分:6)

除非我完全弄错,否则您的代码在数学上是不正确的。

getByte(0x000000ff, 0) {
    24 - 8 * n = 24;
    8 * n = 0;
    0x000000ff << 24 = 0xff000000;
    0xff000000 >> 0 = 0xff000000;
    return 0xff000000; // should return 0xff
}

不允许使用运算符-,尤其是*是一个问题(无法* 8)。我想出了这个:

uint8_t getByte (uint32_t x, int n) {
    switch (n) {
        case 0:
            return x & 0xff;
        case 1:
            return (x >> 8) & 0xff;
        case 2:
            return (x >> 16) & 0xff;
        case 3:
            return x >> 24;
    }
}

不完全漂亮,但它符合问题描述:6个操作员,所有这些都是合法的。

编辑:对于如何避免* 8

,我有一个(非常明显的)想法
uint8_t getByte (uint32_t x, int n) {
    return (x >> (n << 3)) & 0xff;
}

答案 2 :(得分:1)

我不明白你的功能如何运作。试试这个:

int getByte(int x, int n)
{
     return (x >> (8 * n)) & 0xFF;
}