明确指定通用lambda的operator()模板参数是否合法?

时间:2018-03-20 19:34:03

标签: c++ templates lambda language-lawyer generic-lambda

以下C ++代码标准是否合规?

#include <iostream>

int main()
{
    [](auto v){ std::cout << v << std::endl; }.operator()<int>(42);
}

clang ++ 3.8.0 g ++ 7.2.0 compile this code fine(编译器标志为-std=c++14 -Wall -Wextra -Werror -pedantic-errors)。

2 个答案:

答案 0 :(得分:12)

这确实符合标准。该标准规定必须有一个成员operator(),并且在其paramater-declaration-clause中每次出现auto时都有一个模板参数。没有任何措辞禁止明确提供。

行的底部:lambda的调用运算符只是一个普通函数(模板,如果是通用的)。

供参考,相关标准条款:

  

非泛型lambda表达式的闭包类型具有public   内联函数调用操作符(16.5.4),其参数和返回值   type由lambda表达式描述   分别为parameter-declaration-clause和trailing-return-type。   对于通用lambda,闭包类型具有公共内联函数   调用操作员成员模板(17.5.2),其template-parameter-list   每个事件包含一个发明的类型模板参数   lambda的parameter-declaration-clause中的auto,按顺序排列   外观。本发明的类型模板参数是参数包   如果相应的参数声明声明了一个函数   参数包(11.3.5)。返回类型和函数参数   函数调用操作符模板派生自   lambda-expression的trailing-return-type和   参数声明子句通过替换每次出现的auto   带有名称的parameter-declaration-clause的decl-specifiers   相应的发明模板参数。

N4659(C ++ 17)中的

8.1.5.1/3 [expr.prim.lambda.closure],强调我的。

答案 1 :(得分:10)

是的,它似乎定义明确,因为lambdas的模板参数&#39; operator()是严格定义的。

[expr.prim.lambda]/5

  

...
  对于通用lambda,闭包类型具有公共内联函数   调用操作员成员模板(14.5.2),其 template-parameter-list 包含一个发明类型 template-parameter   对于lambda的 parameter-declaration-clause 中每次出现的auto,按出现的顺序排列。
  ...