C++ 依赖型自动演绎

C++ 依赖型自动演绎,c++,c++11,templates,template-meta-programming,type-deduction,C++,C++11,Templates,Template Meta Programming,Type Deduction,是否可以执行以下操作: template<class T, T type> constexpr auto f(/* type used in some way... */) // -> decltype (etc. in case of C++11) { return std::integral_constant<T,t>{}; } constexpr auto z = f(3); // z is deduced as an integral_cons

是否可以执行以下操作:

template<class T, T type>
constexpr auto f(/* type used in some way... */) // -> decltype (etc. in case of C++11)
  {
  return std::integral_constant<T,t>{};
  }

constexpr auto z = f(3); // z is deduced as an integral_constant<int,3>;
模板
constexpr auto f(/*类型以某种方式使用…*/)/->decltype(在C++11中为等)
{
返回std::积分_常量{};
}
constexpr auto z=f(3);//z被导出为积分_常数;
当然不可能使用运行时值,但在本例中,3是编译时值。也许有人知道一些我不知道的把戏

[编辑] constexpr auto z2=f();//这也可以


我只是想避免重复这种类型

您可以在C++17中使用
auto
模板参数:

template <auto T>
constexpr auto f()
{
    return std::integral_constant<decltype(T), T>{};
}
模板
constexpr auto f()
{
返回std::积分_常量{};
}
用法:

f<3>(); // integral_constant<int, 3>
f(int_<3>{});
f();//积分常数

或者,您需要以编译时友好的方式包装您的值:

template <int X>
struct int_ 
{ 
    using type = int;
    static constexpr value = X; 
};

template <typename T>
constexpr auto f(T)
{
    return std::integral_constant<typename T::type, T::value>{};
}
模板
结构内部
{ 
使用type=int;
静态constexpr值=X;
};
样板
constexpr自动f(T)
{
返回std::积分_常量{};
}
用法:

f<3>(); // integral_constant<int, 3>
f(int_<3>{});
f(int{});

您可以在C++17中使用
auto
模板参数:

template <auto T>
constexpr auto f()
{
    return std::integral_constant<decltype(T), T>{};
}
模板
constexpr auto f()
{
返回std::积分_常量{};
}
用法:

f<3>(); // integral_constant<int, 3>
f(int_<3>{});
f();//积分常数

或者,您需要以编译时友好的方式包装您的值:

template <int X>
struct int_ 
{ 
    using type = int;
    static constexpr value = X; 
};

template <typename T>
constexpr auto f(T)
{
    return std::integral_constant<typename T::type, T::value>{};
}
模板
结构内部
{ 
使用type=int;
静态constexpr值=X;
};
样板
constexpr自动f(T)
{
返回std::积分_常量{};
}
用法:

f<3>(); // integral_constant<int, 3>
f(int_<3>{});
f(int{});

由于c++11,您可以声明自己的文本(我在这里使用了
std::index_序列
,它是c++14,但您可以很容易地找到上述的c++11实现):

#包括//用于std::index_序列和std::size_t
constexpr std::size\u t ipow(std::size\u t base,int-exp,std::size\u t result=1){
返回exp<1?结果:ipow(基*基,exp/2,(exp%2)?结果*基:结果);
}
constexpr std::size\t vdot(std::index\u序列,std::index\u序列){
返回0;
}
样板
constexpr std::size\t vdot(std::index\u序列,std::index\u序列){
返回C*ipow(10,I)+vdot(std::index_序列{},std::index_序列{});
}
样板
std::积分常量运算符“”\u ic(){
返回{};
}
int main(){
自动集成电路=3个集成电路;
静态投影(ic);
}

由于c++11,您可以声明自己的文本(我在这里使用的是
std::index_sequence
,它是c++14,但您可以很容易地找到上述的c++11实现):

#包括//用于std::index_序列和std::size_t
constexpr std::size\u t ipow(std::size\u t base,int-exp,std::size\u t result=1){
返回exp<1?结果:ipow(基*基,exp/2,(exp%2)?结果*基:结果);
}
constexpr std::size\t vdot(std::index\u序列,std::index\u序列){
返回0;
}
样板
constexpr std::size\t vdot(std::index\u序列,std::index\u序列){
返回C*ipow(10,I)+vdot(std::index_序列{},std::index_序列{});
}
样板
std::积分常量运算符“”\u ic(){
返回{};
}
int main(){
自动集成电路=3个集成电路;
静态投影(ic);
}

在C++11和C++14中,根据

§14.8.2.5[临时扣除类型]13和14

无法从非类型的类型推断模板类型参数 模板参数。[示例:

模板空f(双a[10][i]);
INTV[10][20];
f(v);//错误:无法推导模板参数T的参数
-[结束示例]

因此,您必须指定一个类型。e、 g.
f(/*…*/)

我非常感谢@Barry教我这个


在C++11和C++14中,根据

§14.8.2.5[临时扣除类型]13和14

无法从非类型的类型推断模板类型参数 模板参数。[示例:

模板空f(双a[10][i]);
INTV[10][20];
f(v);//错误:无法推导模板参数T的参数
-[结束示例]

因此,您必须指定一个类型。e、 g.
f(/*…*/)

我非常感谢@Barry教我这个


谢谢你的回复。我忘了提到这是一个C++11问题。这是我们应该选择C++17的原因之一,因为该代码将是理想的解决方案!不幸的是,第二种方法不符合我想要实现的目标。我想避免像int_这样的结构的创建谢谢你的回复。我忘了提到这是一个C++11问题。这是我们应该选择C++17的原因之一,因为该代码将是理想的解决方案!不幸的是,第二种方法不符合我想要实现的目标。我希望避免像int_这样的结构的创建,我将尝试深入讨论您的解决方案。。但我不认为它能满足我的需要:integral_constantfor instance我将尝试深入了解您的解决方案。。但我不认为它能满足我的需要:比如积分常数