可以将lambda用作非类型模板参数吗? [英] Can lambdas be used as non-type template parameter?

查看:67
本文介绍了可以将lambda用作非类型模板参数吗?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

以下代码合法吗?

template <auto Lambda>
struct A {};

int main () {
  auto lmb = [](int i){return i*i;};
  A<lmb> a;
  return 0;
}

我注意到g ++可以很好地编译,而clang ++返回
错误:非类型模板参数不能具有类型'((main.cpp:...处的lambda)' c)。

I noticed that g++ compiles it fine, while clang++ returns error: a non-type template parameter cannot have type '(lambda at main.cpp:...)'.

推荐答案


可以将lambda用作非类型模板参数吗?

Can lambdas be used as non-type template parameter?

是,其实现已实现 P0732R2-非类型模板参数中的类类型,但 clang ++ 尚未实现。

Yes, with implementations that has implemented P0732R2 - Class types in non-type template parameters but clang++ has not implemented it yet.

来源:
https://en.cppreference.com/w/cpp/compiler_support

请注意,lambda必须至少为 constexpr (默认情况下):

Note that the lambda needs to be at least constexpr (which it is by default):


不存在该说明符时,函数调用运算符将​​为
const无论如何,如果它恰好满足所有 constexpr 函数要求。

但是,您可以添加 constexpr 来获取lambda本身的错误,而不是将其用作模板参数。附带说明:您还可以将其指定为 consteval 以使其用作非类型模板参数。

You can however add constexpr to get an error on the lambda itself instead of when using it as a template parameter. As a side note: You can also specify it to be consteval to make it work as a non-type template parameter.

有状态lambda可以是 constexpr

A stateful lambda can be constexpr:

constexpr auto lmb1 = [](int i) {
    static int x = 0;
    return i*i + ++x;
};

,而lambda是通过引用捕获的,或者是通过拷贝捕获( 可变),不能。可以通过复制 constexpr 进行捕获。

while a lambda capturing by reference, or capturing by copy and mutating (mutable), can not. Capturing by copying a constexpr is ok though.

通用lambda可能是 constexpr 也是:​​

Generic lambdas may be constexpr too:

constexpr auto gen_lmb = []<typename T>(T& val) {
   val += val;
   return val;
};

template <auto Lambda>
struct A {
    template<typename T>
    void doit(T&& arg) {
        std::cout << Lambda(arg) << '\n';
    }
};

//...

A<gen_lmb> ginst;

int v = 1000;
ginst.doit(v);
ginst.doit(std::string("foo "));
std::cout << v << '\n';



2000
foo foo
2000

这篇关于可以将lambda用作非类型模板参数吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆