参数包形式'auto ... arg'在lambda中启用但在函数中没有启用?

时间:2015-03-07 14:51:38

标签: c++ gcc parameters lambda clang

有人可以解释为什么参数可以声明为' auto ... arg'在这种情况下(当在lambda中使用时):

    auto glambda = [](auto a, auto&& b) { return a < b; }; 
    bool b = glambda(3, 3.14); // OK

    auto vglambda = [](auto printer) { 
        return [=](auto ... ts) { // OK: ts is a function parameter pack 
            printer(std::forward<decltype(ts)>(ts)...);
            return [=]() { printer(ts ...); };
        };
    };

    auto p = vglambda( [](auto v1, auto v2, auto v3) { std::cout << v1 << v2 << v3; } ); 

    auto q = p(1, 'a', 3.14); // OK: outputs 1a3.14 q(); // OK: outputs 1a3.14

生命example

但不在此(在函数中使用时):

void func(auto ... arg)
{
}

生命example

我对使用最新的ISO C ++草案引用的详细解释感到非常高兴。或者这是clang编译器的错误?因为它实际上在gcc 5.0下编译得很好。

1 个答案:

答案 0 :(得分:2)

我自己找到了答案。它在'n4296'中的§5.1.2.5中说明:

  

非泛型lambda表达式的闭包类型具有public   内联函数调用操作符(13.5.4),其参数和返回值   type由lambda表达式描述   分别为parameter-declaration-clause和trailing-return-type。   对于通用lambda,闭包类型具有公共内联函数   调用操作员成员模板(14.5.2) 其template-parameter-list   每次出现时都包含一个发明的类型模板参数   在lambda的parameter-declaration-clause中按顺序自动执行   外观 即可。 本发明的类型模板参数是参数包   如果相应的参数声明声明了一个函数   参数包(8.3.5)。的返回类型和函数参数   函数调用操作符模板是从中派生出来的   lambda-expression的trailing-return-type和   parameter-declarationclause通过替换每次出现的auto   带有名称的parameter-declaration-clause的decl-speci-fi   相应的发明模板参数。

这意味着这样的事情:

[](auto ... arg) {}

大致相当于:

template<class ... tmp>
ClosureType::operator()(tmp ... arg);

但是我不知道为什么在正常功能中也不允许这样做。也许有人应该提出它。