C++ 从使用概念定义的函数返回新对象
代码C++ 从使用概念定义的函数返回新对象,c++,gcc,c++-concepts,C++,Gcc,C++ Concepts,代码 #include <type_traits> template <typename N> concept Number = std::is_arithmetic<N>::value; template <typename T> concept VectorXY = requires(T t) { {t.x} -> Number; {t.y} -> Number; }; template <Number
#include <type_traits>
template <typename N>
concept Number = std::is_arithmetic<N>::value;
template <typename T>
concept VectorXY = requires(T t)
{
{t.x} -> Number;
{t.y} -> Number;
};
template <Number N>
struct Vec2
{
N x = 0;
N y = 0;
};
VectorXY operator*(VectorXY v, Number n)
{
return {v.x * n, v.y * n};
// error: returning initializer list
}
int main()
{
Vec2<float> v = Vec2<float>{} * 1;
// error: conversion from 'void' to non-scalar type 'Vec2<float>' requested
}
#包括
模板
概念编号=标准::是算术::值;
模板
概念向量=需要(T)
{
{t.x}->数字;
{t.y}->数字;
};
模板
结构向量2
{
nx=0;
ny=0;
};
向量运算符*(向量v,编号n)
{
返回{v.x*n,v.y*n};
//错误:返回初始值设定项列表
}
int main()
{
vec2v=Vec2{}*1;
//错误:请求从“void”转换为非标量类型“Vec2”
}
锁销:
那么我该如何解决这个问题呢?
解释编译器无法推断返回类型的原因也会有所帮助。
VectorXY
不是一种类型。这是一个用于检查从函数返回的表达式推导出的类型的概念。所述类型推导与推导函数参数的类型是完全独立的
你返回的是
{v.x * n, v.y * n}
它是一个括号内的初始值设定项。在对其进行模板参数推断时,通常会推断出一个std::initializer\u list
。这有两个问题:第一,没有包含相应的头,因此程序的格式不正确。其次,即使包含了头,std::initializer_list
也不满足VectorXY
的概念
您可以通过指定返回对象的类型来修复它,例如通过函数强制转换表示法
return decltype(v){v.x * n, v.y * n};
现在它是一个类型化表达式,根据它,函数的返回类型被推导出满足向量概念的内容
作为附录,GCC还没有实现它,但是正确的语法应该是
VectorXY auto operator*(VectorXY auto v, Number auto n)
{
return decltype(v){v.x * n, v.y * n};
}
考虑到仅仅使用VectorXY
所造成的混乱,我认为委员会要求使用这种受限的auto
语法是正确的。事实上,有一个类型演绎正在进行中,这对我来说更为明显