简体   繁体   English

lambda函数在c ++中的priority_queue中不起作用(使用[&]时)

[英]lambda function doesn't work in priority_queue in c++ (when using [&])

When I am doing Leetcode.com, the following code cannot be compiled. 当我在做Leetcode.com时,无法编译以下代码。

auto cmp=[&](pair<int,int> a, pair<int,int> b){return heightMap[a.first]
         [a.second]<heightMap[b.first][b.second];};

priority_queue<pair<int,int>,vector<pair<int,int>>,decltype(cmp)> pq;

It works well when I use 我使用时效果很好

auto cmp=[](...){return true;}.

But I have to use 但是我必须用

auto cmp=[&](...){...}

because I need to access heightMap in the function. 因为我需要在函数中访问heightMap。

I don't know why this cannot be compiled 我不知道为什么不能编译

I assume you are working at block scope (ie inside a function). 我假设您正在块作用域内(即在函数内部)工作。

The correct code -- for both the [&] and [] cases -- should be: 对于[&][]情况,正确的代码应为:

priority_queue<pair<int,int>,vector<pair<int,int>>, decltype(cmp)> pq(cmp);
//                                                                   ^^^^^

You can see this in the cppreference example . 您可以在cppreference示例中看到这一点。

If you think about it, the definition of pq with only decltype(cmp) can't know about any local variable -- that attachment is only formed in the actual creation of cmp . 如果您考虑一下,仅带有decltype(cmp)pq的定义就不会知道任何局部变量-附件仅在cmp的实际创建中形成。


The reason is that the default constructor for priority_queue is (C++17 [priqueue.cons]): 原因是priority_queue的默认构造函数为(C ++ 17 [priqueue.cons]):

explicit priority_queue(const Compare& x = Compare(), Container&& y = Container());

As you can see, this involves default-constructing an object of type Compare . 如您所见,这涉及默认构造Compare类型的对象。 Prior to C++20, lambdas are not default constructible . 在C ++ 20之前, lambdas不是默认可构造的

The default construction of stateless lambdas was added by P0624 which didn't quite make it into C++17, but does now appear in C++20 drafts. P0624添加了默认的无状态lambda构造,它并没有完全融入C ++ 17,但现在出现在C ++ 20草案中。

Technically a C++17 compiler should reject even the [] version; 从技术上讲,C ++ 17编译器甚至应拒绝[]版本; but it seems some compilers have made a headstart on C++20 support. 但是似乎有些编译器已经在C ++ 20支持上抢占了先机。

I notice that clang++ 6.0.0 actually allows default construction of a lambda specified as [&] when it happens that no variable is actually captured; 我注意到,当实际上没有捕获任何变量时,clang ++ 6.0.0实际上允许默认构造为指定为[&]的lambda。 whereas the wording of P0624 says that that case should be rejected. 而P0624的措辞则表明该案应予驳回。 Perhaps this will change again before C++20 is finalized. 也许这将在C ++ 20完成之前再次改变。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM