C联盟中的Endian交换

时间:2016-05-18 15:50:14

标签: c swap endianness unions

我试图理解在C中的联合内完成endian swap的方式。我理解union可以保存多种类型的数据,但一次只能保存一种类型。我试图理解的代码看起来像这样,这是联合定义:

  union byte4 {
          char byte[4];
          int numint;
          float numfloat;
  };

这是功能。

  int endianSwap4int(int a) {
      union byte4 un;
      un.numint = a;

      // swap
      char c1 = un.byte[0];
      un.byte[0] = un.byte[3];
      un.byte[3] = c1;
      c1 = un.byte[1];
      un.byte[1] = un.byte[2];
      un.byte[2] = c1;

      return un.numint;
  }

在函数中,如果输入a是2048327680,则返回un.numint时函数返回6010。我理解操纵un.byte也间接操纵un.numint因为工会一次只能容纳一件事,但我不明白他们究竟是如何相互影响的,所以我的问题是,它们究竟是如何相互影响的?

1 个答案:

答案 0 :(得分:1)

如果查看2048327680的十六进制表示,您会看到它是7A 17 00 00。因此,如果您的机器以小端格式存储该值,则首先存储LSB。

如果我们向endianSwap4int添加额外调试,如下所示:

  int endianSwap4int(int a) {
      union byte4 un;
      int i;
      un.numint = a;

      printf("before:\n");
      for (i=0;i<4;i++) {
          printf("un[%d]=%02X\n", i, un.byte[i]);
      }

      // swap
      char c1 = un.byte[0];
      un.byte[0] = un.byte[3];
      un.byte[3] = c1;
      c1 = un.byte[1];
      un.byte[1] = un.byte[2];
      un.byte[2] = c1;

      printf("after:\n");
      for (i=0;i<4;i++) {
          printf("un[%d]=%02X\n", i, un.byte[i]);
      }
      return un.numint;
  }

您将看到以下输出:

before:
un[0]=00
un[1]=00
un[2]=17
un[3]=7A
after:
un[0]=7A
un[1]=17
un[2]=00
un[3]=00

在这里,您可以看到原始号码的LSB在交换之前是第一个,并且原始号码的MSB在交换之后是第一个。所以现在联合的int部分包含值00 00 17 7A,其十进制为6010