截至 C++14 起尾随返回类型语法的合法使用
Legitimate uses of the trailing return type syntax as of C++14
实际上有什么理由再使用以下语法:
template<typename T>
auto access(T& t, int i)
-> decltype(t[i])
{
return t[i];
}
现在我们可以使用 :
template<typename T>
decltype(auto) access(T& t, int i)
{
return t[i];
}
尾随返回类型语法现在似乎有点多余?
推导的返回类型对 SFINAE 不友好。如果重载无效,则此重载将简单地退出重载集t[i]
:
template<typename T>
auto access(T& t, int i)
-> decltype(t[i])
{
return t[i];
}
而这种重载不会,导致硬错误:
template<typename T>
decltype(auto) access(T& t, int i)
{
return t[i];
}
演示
此外,您可能会遇到推导返回类型冲突的问题。考虑我是否要返回std::optional<T>
.以下代码无法编译,因为std::nullopt_t
与std::optional<T>
的类型不同:
#include <optional> // C++17 standard library feature
template <typename T>
auto foo(T const& val)
{
if (val.is_invalid()) return std::nullopt;
return val.some_function_returning_an_optional();
}
尾随返回类型允许您准确指定要返回的表达式类型:
template <typename T>
auto foo(T const& val)
-> decltype(val.some_function_returning_an_optional())
{
if (val.is_invalid()) return std::nullopt;
return val.some_function_returning_an_optional();
}
您可以使用前导返回类型,但它需要使用std::declval
,这使得更难理解:
template <typename T>
decltype(std::declval<T const&>().some_function_returning_an_optional())
foo(T const& val)
{
if (val.is_invalid()) return std::nullopt;
return val.some_function_returning_an_optional();
}
演示
是的,至少有三个原因:
- 有意义的声明:你的第一个变体有一个声明,告诉我返回类型是什么;你的第二个变体要求我阅读你的定义。但是您的定义可能在另一个文件中,或者不是很清楚。 类型
- 约束或类型转换:您的主体可能返回表达式
T[i]
以外的内容,因此您将获得类型约束或从主体返回的内容到您想要获取的内容的转换。 - 向后兼容性:这对您来说似乎微不足道,但请尝试编写一个库并告诉您的用户"哦,由于我的语法选择可爱,您需要一个符合 C++14 的编译器"。
贾斯汀的回答中还有第四个原因。
相关文章:
- 如何获取std::result_of函数的返回类型
- 奇怪的结构&GCC&clang(void*返回类型)
- 如何建立使用模板函数的lambda函数的尾部返回类型
- 为什么与常规GCC不同,即使有"学究性错误",MinGW-GCC也能容忍丢失的返回类型
- 在没有定义返回类型的函数中返回布尔值,并将结果保存在无错误的char编译中-为什么
- 特征::矩阵<双精度,1,3> 结构类型函数中的返回类型函数
- 函数作为模板参数,是否对返回类型强制约束
- C++中函数的向量返回类型引发错误
- 检查函数返回类型是否与STL容器类型值相同
- 为什么返回类型中需要typename?C++
- <Windows>为什么 std::thread::native_handle 返回类型为"long long unsigned int"的值,而不是 void*(又名 HANDLE)?
- 警告:在函数返回类型 [-Wignore 限定符] 时忽略类型限定符
- 截至 C++14 起尾随返回类型语法的合法使用
- 返回类型布尔函数中的声明语法错误
- 是否可以在尾随返回类型语法中直接使用参数值(不是其类型,而是值本身)
- 嵌套模板类返回类型在 C++ 中的头文件中函数返回类型的语法
- GCC 中的编译器错误,但在将 decltype 与具有尾随返回类型语法的模板化成员函数一起使用时没有 clang
- 是否可以通过从lambda的引用中返回T型对象,而无需使用尾随返回类型语法
- 在后面的返回类型函数语法中,auto关键字背后是否有意图
- 由于noexcept说明符,尾随返回类型语法失败