代码之家  ›  专栏  ›  技术社区  ›  Guillaume Racicot

lambda可以出现在模板参数中吗[[副本]

  •  3
  • Guillaume Racicot  · 技术社区  · 7 年前

    #include <type_traits>
    
    template <auto>
    struct Foo: std::false_type { };
    
    template <>
    struct Foo<[](){return 1;}()>:std::true_type { };
    
    int main() {
        static_assert(Foo<1>::value);
    }
    

    我知道lambda不能在未赋值的上下文中声明,但显然这里不是这样。更奇怪的是Clang5.0.0(我猜,它首先部分支持constexpr lambda) does compile it .

    是编译器错误还是C++17允许这样?

    0 回复  |  直到 8 年前
        1
  •  25
  •   Rakete1111    7 年前

    gcc 7.1 正确拒绝代码。

    [expr.prim.lambda]/2

    闭包对象 . lambda表达式不应出现在未赋值的操作数中, ,在别名声明、typedef声明或函数或函数模板在其函数体和默认参数之外的声明中。

    这一点在随后的一份说明中也作了明确说明:

    如果我猜的话,我会说这个bug是因为从C++17开始,lambda是隐式的 constexpr ,这使得它们可以在编译时表达式(如模板参数)中有效调用。但实际上在模板参数中定义lambda仍然是非法的。


        2
  •  0
  •   Alexey Mikhailov    6 年前

    # include <cassert>
    
    template<int(*fn)()>
    int get_twice()
    {
        return fn() * 2;
    }
    
    int main()
    {
        int result = get_twice <+[]() { return 42; }> ();
        assert(result == 84);
    }