假设我定义一个这样的联合:
#include <stdio.h>
int main() {
union u {
int i;
float f;
};
union u tst;
tst.f = 23.45;
printf("%d\n", tst.i);
return 0;
}
有人能告诉我存储在哪里的内存tst
会是什么样子吗?
我试图了解1102813594
该程序产生的输出。
假设我定义一个这样的联合:
#include <stdio.h>
int main() {
union u {
int i;
float f;
};
union u tst;
tst.f = 23.45;
printf("%d\n", tst.i);
return 0;
}
有人能告诉我存储在哪里的内存tst
会是什么样子吗?
我试图了解1102813594
该程序产生的输出。
这取决于实现(编译器、操作系统等),但如果需要,您可以使用调试器实际查看内存内容。
例如,在我的 MSVC 2008 中:
0x00415748 9a 99 bb 41
是内存内容。从左侧的 LSB(Intel,little-endian 机器)读取,这是 0x41bb999a 或实际上是 1102813594。
但是,通常整数和浮点数存储在相同的字节中。根据您访问联合的方式,您可以获得这些字节的整数或浮点解释。同样,内存空间的大小取决于实现,尽管它通常是与某个固定边界对齐的最大组成部分。
为什么在您(或我的)案例中具有这样的价值?您应该阅读有关浮点数表示的信息(查找 ieee 754)
结果取决于编译器的实现,但对于大多数 x86 编译器,float 和 int 的大小相同。维基百科有一个很好的 32 位浮点布局图http://en.wikipedia.org/wiki/Single_precision_floating-point_format,可以帮助解释1102813594
。
如果将 int 打印为十六进制值,将更容易计算出来。
printf("%x\n", tst.i);
使用联合,两个变量都存储在相同的内存位置。浮点数以 IEEE 格式存储(不记得标准编号,您可以查看[编辑:正如其他人指出的,IEEE 754])。但是,它将是一个二进制补码归一化(尾数始终在 0 和 10 之间,指数可以是任何值)浮点数。
您正在获取该数字的前 4 个字节(再次,您可以查找浮点数占用的 16 位或 32 位中的哪些位,不记得了)。所以它基本上没有任何意义,它作为 int 没有用。也就是说,除非您知道为什么要执行此类操作,但通常情况下,float 和 int 组合并不是很有用。
而且,不,我认为它不是实现定义的。我相信标准规定了浮点数的格式。
在联合中,成员将共享相同的内存。这样我们就可以将浮点值作为整数值。
浮点数格式将不同于整数存储。这样我们就可以理解使用联合的区别。
例如:如果我将 12 个整数值存储在(32 位)中。我们可以将这 12 个值作为浮点格式。
它将存储为有符号(1 位)、指数(8 位)和有效精度(23 位)。
我写了一个小程序,展示了将 32 位浮点数的位模式保存为 32 位整数时会发生什么。它为您提供了与您遇到的完全相同的输出:
#include <iostream>
int main()
{
float f = 23.45;
int x = *reinterpret_cast<int*>(&f);
std::cout << x; // 1102813594
}