#include <string>
#include <type_traits>
class C
{
static auto func() { return std::string("hello"); }
static_assert(std::is_same<decltype(func()), std::string>::value, "");
};
GCC和Clang都不接受这一点,说func
在定义之前就已使用了。为什么呢?
将推断的auto
返回类型更改为std::string
使其有效。
答案 0 :(得分:3)
decltype
构造生成标识符或表达式的声明类型。当使用返回类型声明func
时,调用表达式func()
的类型是已知的,并且一切都按预期工作。
但是,当使用返回类型占位符func
声明auto
时,func
的声明取决于其定义,因此{的类型在定义函数之前,{1}}以及表达式func
是未知的。
当你在类定义中内联定义一个类成员函数时,就好像定义是在类定义结束后出现的那样(也就是说,函数体可以引用词法声明的名称< em>稍后在类定义中)。这个的结果和func()
的语义是你的函数auto
实际上并没有完全声明直到类定义结束,因此{{1}的类型直到那时才能知道。
答案 1 :(得分:1)
除了其他答案之外,可能的解决方法是将检查推迟到静态函数,并依靠优化器删除所有冗余代码。
在发布版本中,这应该是零成本:
#include <string>
#include <type_traits>
#include <iostream>
struct C
{
static auto func() {
check_same();
return std::string("hello");
}
private:
static void check_same()
{
static_assert(std::is_same<decltype(func()), std::string>::value, "");
}
};
int main()
{
std::cout << C::func() << '\n';
}