将float转换为unsigned long以访问c #define中的float内部

Arn*_*ard 5 c floating-point floating-point-conversion

我想将转换floatunsigned long,同时保持的二进制表示float(所以我希望投5.05!).

这很容易通过以下方式完成:

float f = 2.0;
unsigned long x = *((unsigned long*)&f)
Run Code Online (Sandbox Code Playgroud)

但是,现在我需要在a中做同样的事情#define,因为我想稍后在一些数组初始化中使用它(所以[inline]函数不是一个选项).

这不编译:

#define f2u(f) *((unsigned long*)&f)
Run Code Online (Sandbox Code Playgroud)

如果我这样称呼它:

unsigned long x[] = { f2u(1.0), f2u(2.0), f2u(3.0), ... }
Run Code Online (Sandbox Code Playgroud)

我得到的错误是(逻辑上):

lvalue required as unary ‘&’ operand
Run Code Online (Sandbox Code Playgroud)

注意:下面建议的一个解决方案是union为我的数组使用一个类型.但是,这是没有选择的.我实际上在做以下事情:

#define Calc(x) (((x & 0x7F800000) >> 23) - 127)
unsigned long x[] = { Calc(f2u(1.0)), Calc(f2u(2.0)), Calc(f2u(3.0)), ... }
Run Code Online (Sandbox Code Playgroud)

所以数组真的/必须是类型long[].

MBy*_*ByD 1

lvalue意味着可分配的东西。 1.0是一个常量,而不是变量,并且您无法获取对它的引用(也无法分配给它)。

意义:

这:

unsigned long x[3] = { f2u(1.0), f2u(2.0), f2u(3.0) }
Run Code Online (Sandbox Code Playgroud)

实际上是:

unsigned long x[3] = { *((unsigned long*)&1.0, *((unsigned long*)&2.0, *((unsigned long*)&3.0 }
Run Code Online (Sandbox Code Playgroud)

1.02.0并且3.0没有地址。

问题与定义无关,#define因为定义是一个简单的替换,此代码也无效:

unsigned long x = *((unsigned long*)&1.0;
Run Code Online (Sandbox Code Playgroud)

问题是您试图引用没有地址的立即值。