【问题标题】:Three-way comparison of pointer to functions fails函数指针的三向比较失败
【发布时间】:2020-06-22 12:31:46
【问题描述】:

为什么我不能用 GCC 主干比较指向函数的指针?

using f_t = int(*)(int);
f_t a { nullptr }, b { nullptr };
auto c = a <=> b;

int main (){}

给予

a.cpp:4:13: error: invalid operands of types ‘f_t’ {aka ‘int (*)(int)’} and ‘f_t’ {aka ‘int (*)(int)’} to binary ‘operator<=>’
    4 | auto c = (a <=> b) == 0;
      |           ~ ^~~ ~
      |           |     |
      |           |     f_t {aka int (*)(int)}
      |           f_t {aka int (*)(int)}

【问题讨论】:

  • &lt;=&gt; 不相等时,您期望返回什么?函数的地址甚至不如普通地址有用(编译之间会有所不同,如果一个函数来自加载了 ASLR 的单独 DLL/共享对象,则甚至会因运行而异);确定哪个“较小”和哪个“更大”没有任何用处。 Earlier C++ specs only defined ==/!= for function pointers;我不希望他们从那以后扩展它。
  • 这能回答你的问题吗? How to compare pointers?

标签: c++ c++20 spaceship-operator


【解决方案1】:

在函数指针上使用普通关系运算符的结果是unspecified if the pointers are unequal。您可以比较指向对象的指针(但只有当它们是指向同一数组或结构的指针时才有意义),但关联函数指针实际上并不可行。

而不是采取有时未指定的路线,C++20 simply forbids using &lt;=&gt; for non-object pointers

您可以测试这些指针之间的相等性,但不能测试它们的相对顺序。如果您出于某种原因绝对需要这样做,您可以将指针转换为 void*s 并使用 std::less&lt;&gt; 进行此类比较。

【讨论】:

  • void*s 上的比较是否已定义?
  • 好的,但是auto d = a &lt; b; 确实可以编译。
  • @Barry:应用于指针时适用于std::less。也就是说,如果将函数指针转换为void* 是一个定义明确的操作(这实际上不是必需的),那么std::less 必须提供此类指针的明确定义的总顺序。
猜你喜欢
  • 2012-10-05
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-11-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多