在没有 implicit/explicit 转换的情况下在 C 中查找字节顺序

Finding Endianness in C without implicit/explicit casting

我期待找到一种方法,借此我可以找到字节顺序 而无需 implicit/explicit 强制转换、循环、切换、内置函数、宏 。我试过一段代码,但它使用显式转换。

int is_little_endian(){
    int temp = 1;
    return *(char *) temp;//Returns 1 if it's a little endian machine.
}

[编辑]

必须在不使用任何转换的情况下完成。我找不到一个问题,我们可以在不强制转换和使用宏的情况下做到这一点。 Implicit Casting 这里指的是编译器自动转换。说从 char 到 int。

为什么不试试

unsigned int i= 1;
char *p = &i;

if(*p)
    printf("Little endian\n");
else
    printf("Big endian\n");

没有 "implicit casting" 这样的东西 - 强制转换是一个显式运算符。但是,如果您正在寻找一种无需检查对象的 表示 即可观察字节序的方法,那么没有办法。 Endianness 纯粹是 属性 表示,而不是值,因此如果您限制自己访问表示,它就不存在。这就是为什么大多数好的代码不应该关心字节顺序的原因。

如果您确实想作弊并访问表示,但又不想让它看起来像演员,这里有一些想法:

int i = 1;
char c;
memcpy(&c, &i, 1);
c;

或:

union { int i; char c; } x = { 1 };
x.c;

或:

int i = 1;
FILE *f = tmpfile();
fwrite(&i, sizeof i, 1, f);
rewind(f);
getc(f);

或使用任何可能在后台为您执行此类操作的库函数。如果您使用的是 POSIX 系统或任何其他具有套接字操作的系统,您也可以:

htonl(1) != 1;

但是所有这些要么依赖于检查表示,要么依赖于实现中关于目标字节序是什么的硬编码假设。

这是通过编译器本身完成的。

int is_little_endian(void) {
#ifdef _LITTLE_ENDIAN
    return 1;
#else
    return 0;
#endif
}

为小端目标构建程序时,在构建命令中定义_LITTLE_ENDIAN(通常通过添加-D_LITTLE_ENDIAN)。如果程序是为大端目标构建的,请在构建命令中定义 _BIG_ENDIAN (-D_BIG_ENDIAN).

以上示例将在 运行 时让您知道它是否是为小端目标构建的。

但是,由于字节顺序不太可能在 运行 时更改,我认为在 运行 时这样做没有多大价值。而是利用 C 预处理器和通过命令行传入定义的能力来完成您需要的。

希望对您有所帮助。