如何解释*((char *)& a)

时间:2012-08-28 14:30:55

标签: c endianness

我看到一种方法可以知道平台的字节顺序是这个程序,但我不明白

#include <stdio.h>
int main(void)
{
  int a = 1;
  if( *( (char*)&a ) == 1) printf("Little Endian\n");
  else printf("Big Endian\n");
  system("PAUSE");  
  return 0;
}

测试做了什么?

8 个答案:

答案 0 :(得分:9)

int几乎总是大于一个字节,并且经常跟踪架构的字大小。例如,32位架构可能具有32位整数。因此,给定典型的32位整数,4字节的布局可能是:

   00000000 00000000 00000000 00000001

或首先使用最低有效字节:

   00000001 00000000 00000000 00000000

char *是一个字节,所以如果我们将这个地址转换为char *,我们将得到上面的第一个字节,

   00000000

   00000001

因此,通过检查第一个字节,我们可以确定架构的字节顺序。

答案 1 :(得分:4)

这只适用于sizeof(int) > 1的平台。举个例子,我们假设它是2,而char是8位。

基本上,对于little-endian,作为16位整数的数字1如下所示:

00000001 00000000

但是对于big-endian,它是:

00000000 00000001

首先,代码集a = 1,然后是:

*( (char*)&a ) == 1)

获取a的地址,将其视为指向char的指针,然后取消引用它。所以:

  • 如果a包含小端整数,那么您将获得00000001部分,当char

    <时,它会为1 / LI>
  • 如果a包含一个大端整数,那么您将获得00000000。对== 1的检查将失败,代码将假定该平台是big-endian。

您可以使用int16_tint8_t代替intchar来改进此代码。或者更好的是,只需检查htons(1) != 1

答案 2 :(得分:2)

  1. a
  2. 的地址
  3. 将其投放到char*
  4. 取消引用此char*,这将为您提供int
  5. 第一个字节
  6. 检查它的值 - 如果它是1,那么它是小端。否则 - 大。

  7. 假设sizeof(int) == 4,然后:

    |........||........||........||........|    <- 4bytes, 8 bits each for the int a
    | byte#1 || byte#2 || byte#3 || byte#4 |
    

    当执行第1,2和3步时,*( (char*)&a )将为您提供第一个字节| byte#1 |

    然后,通过检查byte#1的值,您可以了解它是大端还是小端。

答案 3 :(得分:2)

  • 您可以将整数视为4个字节的数组(在大多数平台上)。小端整数将具有值01 00 00 00和大端00 00 00 01
  • 通过执行&a,您将获得该数组的第一个元素的地址。
  • 表达式(char*)&a将其转换为单个字节的地址。
  • 最后*( (char*)&a )获取该地址所包含的值。

答案 4 :(得分:1)

程序只是将int占用的空间重新解释为char的数组,并假设1作为int将被存储为一系列字节,最低其顺序为值为1的字节,其余为0。

因此,如果最低位字节首先出现,则平台是小端,否则是大端。

这些假设可能不适用于所有存在的平台。

答案 5 :(得分:1)

a = 00000000 00000000 00000000 00000001
    ^                                 ^
    |                                 |
    &a if big endian                  &a if little endian

    00000000                   00000001
    ^                                 ^
    |                                 |
    (char*)&a for BE                  (char*)&a for LE

    *(char*)&a = 0 for BE             *(char*)&a = 1 for LE

答案 6 :(得分:1)

以下是它如何分解:

           a        -- given the variable a
          &a        -- take its address; type of the expression is int *
  (char *)&a        -- cast the pointer expression from type int * to type char *
*((char *)&a)       -- dereference the pointer expression
*((char *)&a) == 1  -- and compare it to 1

基本上,强制转换(char *)&a将表达式&a的类型从指向int的指针转换为指向char的指针;当我们将解除引用运算符应用于结果时,它为我们提供了存储在a的第一个字节中的值。

答案 7 :(得分:0)

*( (char*)&a )

在BigEndian数据中,int i = 1(大小为4字节)将在内存中排列为: - (从较低地址到较高地址)。

00000000 -->Address 0x100
00000000 -->Address 0x101
00000000 -->Address 0x102
00000001 -->Address 0x103

LittleEndian是: -

00000001 -->Address 0x100
00000000 -->Address 0x101
00000000 -->Address 0x102
00000000 -->Address 0x103

分析以上演员: -

同样&a= 0x100因此 *((char*)0x100)意味着考虑一个字节(因为为int加载了4个字节)一次,所以将引用0x100处的数据。

*( (char*)&a ) == 1 => (*0x100 ==1) that is 1==1 and so true,implying its little endian.