【问题标题】:Abbreviated function template vs. function template with forwarding reference param缩写函数模板与带有转发参考参数的函数模板
【发布时间】:2016-04-27 09:45:59
【问题描述】:

两者有什么区别 带有转发参考参数的函数模板

template<typename T>
void Universal_func(T && a)
{
}

缩写函数模板

void auto_fun(auto && a)
{
}

我可以用auto_fun 替换Universal_func 吗? Universal_funcauto_fun 还是相等的?

我已经测试了下面的程序。好像两者都是一样的。

template<typename T>
void Universal_func(T && a)
{
}

void auto_fun(auto && a)
{
}

int main()
{
  int i;   
  const int const_i = 0; 
  const int const_ref =const_i; 
  //forwarding reference template function example  
  Universal_func(1); //call void Universal_func<int>(int&&)
  Universal_func(i);//call void Universal_func<int&>(int&):
  Universal_func(const_i); //call void Universal_func<int const&>(int const&)
  Universal_func(const_ref);//call void Universal_func<int const&>(int const&)

  //auto calls  
  auto_fun(1); //call void auto_fun<int>(int&&)
  auto_fun(i);//call void auto_fun<int&>(int&):
  auto_fun(const_i); //call void auto_fun<int const&>(int const&)
  auto_fun(const_ref);//call void auto_fun<int const&>(int const&)
  return 0;
}

Universal_funcauto_fun 推导和扩展为类似的功能。

void Universal_func<int>(int&&):
        pushq   %rbp
        movq    %rsp, %rbp
        movq    %rdi, -8(%rbp)
        nop
        popq    %rbp
        ret
void Universal_func<int&>(int&):
        pushq   %rbp
        movq    %rsp, %rbp
        movq    %rdi, -8(%rbp)
        nop
        popq    %rbp
        ret
void Universal_func<int const&>(int const&):
        pushq   %rbp
        movq    %rsp, %rbp
        movq    %rdi, -8(%rbp)
        nop
        popq    %rbp
        ret
void auto_fun<int>(int&&):
        pushq   %rbp
        movq    %rsp, %rbp
        movq    %rdi, -8(%rbp)
        nop
        popq    %rbp
        ret
void auto_fun<int&>(int&):
        pushq   %rbp
        movq    %rsp, %rbp
        movq    %rdi, -8(%rbp)
        nop
        popq    %rbp
        ret
void auto_fun<int const&>(int const&):
        pushq   %rbp
        movq    %rsp, %rbp
        movq    %rdi, -8(%rbp)
        nop
        popq    %rbp
        ret

有什么不同吗?标准是怎么说的?

【问题讨论】:

  • 带参数 auto 的函数不是标准 C++。
  • @Zereges 不,不是。 Lambda 可以有 auto 参数 IIRC,但函数肯定还没有。
  • @Zereges 我认为在 C++14 中,只有 lambda 参数列表可以使用 auto。其他功能处于Concepts TS阶段。
  • 它不是 C++14 主线的一部分。带有 auto 的函数可能会在 C++17 中作为“通用函数”添加。
  • 它被 GCC 接受为扩展(不使用 -pentatic),它不是标准的 C++,至少现在还不是。

标签: c++ templates c++14 type-deduction template-argument-deduction


【解决方案1】:

函数参数中的auto 还不是标准 C++ 的一部分,但一些最新版本的 GCC 允许将此作为​​扩展,作为其对 Concepts TS 支持的一部分。

Concepts TS 将此构造称为缩写函数模板(尽管它曾经被称为通用函数,我认为这个术语太笼统了) .规则可能太大而无法转入此答案,但请查看 [dcl.fct]/16-19 in this draft 了解所有血腥细节。

第 16 段提供了一个不错的概述:

缩写函数模板是一个函数声明,其参数类型列表包括 一个或多个占位符 (7.1.6.4)。缩写函数模板等价于函数 模板(14.6.6),其模板参数列表包括一个发明的模板参数 parameter-declaration-clause 中每次出现的占位符,按出现顺序, 根据以下规则。 [注:模板参数也被发明来推断 当声明的类型包含占位符时,变量的类型或函数的返回类型 (7.1.6.4.1)。 ——尾注]

根据该草案中规定的规则,您的两个定义在功能上是等效的。

我们采用占位符参数的函数:

void auto_fun(auto && a)
{
}

并发明一个模板参数来替换它:

template <typename T>
void auto_fun (T && a)
{
}

如您所见,这与您的函数具有相同的签名,但没有占位符:

template <typename T>
void Universal_func(T && a)
{
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-12-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-12-05
    • 1970-01-01
    • 2013-02-13
    相关资源
    最近更新 更多