尝试在 C++ 中转换结构时出现奇怪的错误消息

Odd error message when trying to cast a structure in C++

在 Linux 上使用 C++,我只是相当愚蠢地写了这个:

struct in_addr ip_addr = ((struct sockaddr_in)socket_addr).sin_addr;

而不是预期的:

struct in_addr ip_addr = ((struct sockaddr_in*)&socket_addr)->sin_addr;

给我这个错误:

"error: no matching function for call to ‘sockaddr_in::sockaddr_in(sockaddr&)"

我知道为什么会出现错误(我正在尝试转换结构),但我不明白为什么错误消息说明了它的作用。有人可以解释一下吗?

当对类型(而不是指针)进行转换时,编译器会尝试调用 sockaddr_in 的构造函数,该构造函数采用与 socket_addr 相同类型的对象。由于该构造函数不存在,编译器会抛出您显示的错误。

当编译器遇到 C 风格转换时,it tries to interpret it as one or two C++-style casts,顺序如下:

  • const_cast<new_type>(expression)
  • static_cast<new_type>(expression)
  • static_cast (with extensions) 后跟 const_cast
  • reinterpret_cast<new_type>(expression)
  • reinterpret_cast 后跟 const_cast

满足各自cast算子要求的优先选择,即使无法编译。

在您的情况下,选择了 static_cast<sockaddr_in>(socket_addr)。这是 direct initialization,因此编译器查找但未找到采用 const 对正在转换的对象的引用的构造函数。

请注意,相同的转换应用于指针时不会触发错误,因为语言具有不同类型指针之间的内置转换。

因为这就是转换的工作方式——它们将 A 转换为 B,并且(除非 B 是指针或引用)需要调用转换运算符或构造函数。编译器试图找到一个构造函数来从 sockaddr 创建一个 sockaddr_in; none 存在,因此出现错误。

无法猜测您真的打算尝试转换为其他东西。

我发现,要成为一名高效的 C++ 程序员,很大一部分就是学习利用这些编译器错误的艺术,并使用它们来启发式地确定 实际 问题可能是什么. ;)