以下内容无法在 gcc 和 clang 上编译
#include <type_traits>
int foo();
int main()
{
using R = std::result_of_t<decltype(foo)()>; // error
}
两个编译器上的错误都涉及声明返回函数的函数的非法性。但我不是在声明这样的函数 - 我只是想写它的类型 - 因为这是result_of
期望的。这真的还是畸形的吗?
您正在传递一个类型 ID,该 ID 在 [dcl.name] 中定义为
[...]语法上是该类型的变量或函数的声明,省略了实体的名称。[...]如果构造是声明中的声明符,则可以唯一标识抽象声明符中标识符出现的位置。然后,命名类型与 假设标识符。
要使假设标识符具有某种类型,假设声明必须首先格式正确。但它不是按照[dcl.fct]/10。因此,程序格式不正确(编译器的错误消息实际上是可以理解的)。这种情况也更直接地被 [temp.deduc]/(8.10) 覆盖,这意味着这是一个(SFINAE 友好的)错误。
事实上,仅仅暗示无效类型的用法就足以使程序格式错误。 例如,创建指向函数返回函数的类型指针格式不正确:
using f = int();
using t = f(*)();
如下:
struct A {virtual void f() = 0;};
using t = A(*)();
(Clang不应该接受这一点。 C.f. GCC bug 17232 的有趣讨论)。