类型推导lambda的参考文献

时间:2015-05-14 15:10:45

标签: c++

我看到了this answer,但我并不满意:它在标准中的哪个类型扣除了' auto'不考虑默认参数?

int main() {
    auto lambda = [] (auto subl = [] {}) {};
    lambda();
}

3 个答案:

答案 0 :(得分:3)

auto根据模板参数推断使用规则([dcl.spec.auto] / P7):

  

如果占位符是自动    type-specifier ,推导出的类型是使用模板参数推导的规则确定的。

当默认参数的类型是推导出的模板参数([temp.deduct.type] / p5)时,默认参数显式为非推导的上下文:

  

未推断的上下文是:

     
    

- 使用 qualified-id 指定的类型的嵌套名称说明符。

         

- decltype-specifier 的表达式。

         

- 非类型模板参数或子表达式引用模板的数组     参数。

         

- 在具有默认参数的函数参数的参数类型中使用的模板参数     在正在进行参数推断的调用中使用。

  

答案 1 :(得分:1)

来自 [expr.prim.lambda]

  

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

无法从默认参数中推导出模板参数;的 [temp.deduct.call]

  

5 - [...] [注意:如果 template-parameter 未在任何一个中使用   函数模板的函数参数,或仅在非推导的上下文中使用,其对应的 template-argument 不能从函数调用中推导出来, template-argument 必须明确地说   指定。 -end note ]

默认参数是非推断的上下文( [temp.deduct.type] / 5)。

答案 2 :(得分:0)

只是添加到上面所说的内容,lamda中的默认参数可以让你在捕获列表时“作弊”。 我们都知道你必须用捕获列表“捕获”外部参数:

int x=7;
auto func = [&x](){ return x+1 ;}

如果您可以使用默认参数,您可以在捕获列表上“作弊”,只需使用默认参数放置引用:

int x=7;
auto func = [](const int& y = x){ return y+1 ;}

阻止默认参数可防止您不捕获外部参数。