mah*_*esh 13 c c++ compiler-construction types casting
如何在不丢失编译器内部数据的情况下进行类型转换?
例如:
int i = 10;
UINT k = (UINT) k;
float fl = 10.123;
UINT ufl = (UINT) fl; // data loss here?
char *p = "Stackoverflow Rocks";
unsigned char *up = (unsigned char *) p;
Run Code Online (Sandbox Code Playgroud)
编译器如何处理这种类型转换?显示位的低级示例将受到高度赞赏.
Joh*_*itb 20
好吧,首先请注意,强制转换是将一种类型的值转换为另一种类型的值的显式请求.强制转换也总是会产生一个新对象,这是一个由强制转换操作符返回的临时对象.但是,转换为引用类型不会创建新对象.该值引用的对象将重新解释为不同类型的引用.
现在回答你的问题.请注意,转换有两种主要类型:
-1
例如,如果为无符号类型对象分配a,会有规则.在某些情况下,错误的转换可能会导致未定义的行为.如果指定的double大于浮点数可以存储到float的值,则不会定义行为.让我们来看看你的演员阵容:
int i = 10;
unsigned int k = (unsigned int) i; // :1
float fl = 10.123;
unsigned int ufl = (unsigned int) fl; // :2
char *p = "Stackoverflow Rocks";
unsigned char *up = (unsigned char *) p; // :3
Run Code Online (Sandbox Code Playgroud)
unsigned int
.如果整数是负数,则该值基本上会包围unsigned int的最大值(参见4.7/2).10.123
被截断为10.这里,不造成丢失的信息,很明显.当10适合unsigned int时,定义了行为.char*
.但是我们在这里忽略它.(见这里).更重要的是,如果你转换为无符号类型会发生什么?实际上,每个5.2.10/7都没有指定结果(注意该转换的语义与在这种情况下使用reinterpret_cast相同,因为这是唯一能够做到这一点的C++转换):指向对象的指针可以显式转换为指向不同类型对象的指针.除了将"指向T1的指针"的rvalue转换为"指向T2的指针"类型(其中T1和T2是对象类型,T2的对齐要求不比T1更严格)并返回其原始类型时原始指针值,这种指针转换的结果是未指定的.
因此,char *
再次强制转换后,只能安全地使用指针.
在您的示例中,两个C风格的演员阵容是不同类型的演员.在C++中,您通常会编写它们
unsigned int uf1 = static_cast<unsigned int>(fl);
Run Code Online (Sandbox Code Playgroud)
和
unsigned char* up = reinterpret_cast<unsigned char*>(p);
Run Code Online (Sandbox Code Playgroud)
第一个执行算术转换,它会截断浮点数,因此会丢失数据.
第二个不对数据进行任何更改 - 它只是指示编译器将指针视为不同的类型.这种演员需要注意:它可能非常危险.
C和C++中的"Type"是在编译器中处理变量时赋给变量的属性.除了C++中的虚函数/ RTTI之外,该属性在运行时不再存在.
编译器使用变量类型来确定很多东西.例如,在将float赋值给int时,它将知道它需要转换.两种类型都可能是32位,但具有不同的含义.CPU可能有一条指令,但编译器会知道调用转换函数.即
& __stack[4] = float_to_int_bits(& __stack[0])
从char*到unsigned char*的转换甚至更简单.这只是一个不同的标签.在位级,p和up是相同的.编译器只需要记住*p需要符号扩展而*up不需要.
归档时间: |
|
查看次数: |
14635 次 |
最近记录: |