8
typedef union status
{
    int nri;
    char cit[2];
}Status;

int main()  {
    Status s;
    s.nri = 1;
    printf("%d \n",s.nri);
    printf("%d,%d,\n",s.cit[0],s.cit[1]);
}

出力:

1
0,1

2行目のこの出力は、CPUのエンディアンに依存していることがわかります。プラットフォームに依存しないプログラムでどのように書くことができますか? CPU のエンディアンを確認する方法はありますか?

4

3 に答える 3

4

htonl()および/またはntohl()を使用できます。htonl()は「ホストからネットワークへのロング」をntohl()表し、「ネットワークからホストへのロング」を表します。「ホスト」と「ネットワーク」はバイトオーダーを指します。ネットワーク バイト オーダーは「ビッグ エンディアン」です。ホスト プラットフォームも「ビッグ エンディアン」の場合、操作はノーオペレーションになります。これらのルーチンを使用すると、次のプログラムは常に同じ出力を報告します。

uint32_t x = htonl(1);
unsigned char *p = (void *)&x;
printf("%u %u %u %u\n", p[0], p[1], p[2], p[3]);
uint32_t y = ntohl(x);
assert(y == 1);
于 2013-09-18T04:56:00.600 に答える
2

エンディアンに依存しないコードが必要な場合は、プラットフォームに依存しないコードも必要です。そうでない場合、要件は意味がありません。エンディアンに依存しないコードは、int のサイズや char の符号に依存できません。

本当にポータブルなものを得るには、次のようなものを書く必要があると思います:

#include <stdio.h>
#include <stdint.h>

#define INT_BITS (sizeof(int) * 8)

#define BYTE0_MASK (0xFFu << (INT_BITS -  8))
#define BYTE1_MASK (0xFFu << (INT_BITS - 16))

int main()
{
  int i = 0xAABBCCDD;
  unsigned char arr [2] =
  {
    (i & BYTE0_MASK) >> (INT_BITS -  8),
    (i & BYTE1_MASK) >> (INT_BITS - 16)
  };

  printf("%x %x", arr[0], arr[1]);    
}
于 2013-09-18T07:00:37.463 に答える