命名空间
变体
操作

强制类型转换运算符

来自 cppreference.com
< c‎ | 语言

执行显式类型转换

内容

[编辑] 语法

( 类型名称 ) 表达式

其中

类型名称 - 类型 void 或任何 标量类型
表达式 - 任何 表达式标量类型(除非 类型名称 为 void,在这种情况下它可以是任何东西)

[编辑] 解释

如果 类型名称void,则 表达式 被求值为其副作用,其返回值被丢弃,就像当 表达式 单独使用时一样,作为 表达式语句

否则,如果 类型名称 恰好是 表达式 的类型,则什么都不做(除了如果 表达式 具有浮点类型并以比其类型指示的更大的范围和精度表示 - 参见下文)

否则,表达式 的值将转换为 类型名称 命名的类型,如下所示

允许通过赋值进行的所有 隐式转换

除了隐式转换外,还允许以下转换

  • 任何整数可以强制转换为任何指针类型。除了空指针常量,如 NULL不需要强制转换),结果是实现定义的,可能无法正确对齐,可能不指向引用的类型对象,并且可能是一个 陷阱表示
  • 任何指针类型都可以强制转换为任何整数类型。结果是实现定义的,即使对于空指针值也是如此(它们不一定导致值为零)。如果结果不能在目标类型中表示,则行为是未定义的(无符号整数在从指针强制转换时不执行模运算)
  • 任何指向对象的指针可以强制转换为任何其他指向对象的指针。如果该值没有针对目标类型正确对齐,则行为是未定义的。否则,如果该值转换回原始类型,则它与原始值进行比较相等。如果指向对象的指针被强制转换为指向任何字符类型的指针,则结果指向对象的最低字节,并且可以递增到目标类型的 sizeof(换句话说,可以用来检查 对象表示 或通过 memcpymemmove 进行复制)。
  • 任何指向函数的指针可以强制转换为指向任何其他函数类型的指针。如果转换后的指针转换回原始类型,则它与原始值进行比较相等。如果转换后的指针用于进行函数调用,则行为是未定义的(除非函数类型是 兼容的)。
  • 在指针之间进行强制转换(对象或函数)时,如果原始值为其类型的空指针值,则结果是目标类型的正确空指针值。

在任何情况下(在执行隐式转换和相同类型转换时),如果 表达式类型名称 是浮点类型,并且 表达式 以比其类型指示的更大的范围和精度表示(参见 FLT_EVAL_METHOD),则范围和精度将被剥离以匹配目标类型。

强制类型转换表达式的 值类别 始终是非左值。

[编辑] 注释

由于 constvolatilerestrict_Atomic 限定符仅对 左值 有效,因此强制转换为 cvr 限定类型或原子类型与强制转换为相应的非限定类型完全相同。

强制转换为 void 有时可用于消除编译器关于未使用的结果的警告。

此处未列出的转换不允许。特别是,

  • 指针和浮点类型之间没有转换
  • 指向函数的指针和指向对象的指针之间没有转换(包括 void*

如果实现提供了 intptr_t 和/或 uintptr_t,则从指向对象类型的指针(包括 cv void)到这些类型的强制转换始终是定义良好的。但是,这对于函数指针并不保证。

(自 C99 起)

请注意,函数指针和对象指针之间的转换被许多编译器接受为扩展,并且被 POSIX dlsym() 函数 的某些用法所期望。

[编辑] 示例

#include <stdio.h>
 
int main(void)
{
    // examining object representation is a legitimate use of cast
    double d = 3.14;
    printf("The double %.2f (%a) is: ", d, d);
    for (size_t n = 0; n < sizeof d; ++n)
        printf("0x%02x ", ((unsigned char*)&d)[n]);
 
    // edge cases
    struct S { int x; } s;
//    (struct S)s; // error; not a scalar type
                   // even though casting to the same type does nothing
    (void)s; // okay to cast any type to void
}

可能的输出

The double 3.14 (0x1.91eb851eb851fp+1) is: 0x1f 0x85 0xeb 0x51 0xb8 0x1e 0x09 0x40

[编辑] 参考文献

  • C23 标准(ISO/IEC 9899:2024)
  • 6.5.4 强制类型转换运算符(页码:待定)
  • C17 标准(ISO/IEC 9899:2018)
  • 6.5.4 强制类型转换运算符(页码:65-66)
  • C11 标准(ISO/IEC 9899:2011)
  • 6.5.4 强制类型转换运算符(页码:91)
  • C99 标准(ISO/IEC 9899:1999)
  • 6.5.4 强制类型转换运算符(页码:81)
  • C89/C90 标准(ISO/IEC 9899:1990)
  • 3.3.4 强制类型转换运算符

[编辑] 参见

C++ 文档 用于 显式类型转换