我正在创建一个程序,它有一个包含 shared_ptr 的映射。当我尝试使用 std::find_if
在其中查找元素时,shared_ptr 的引用计数会增加。示例:
#include <iostream>
#include <memory>
#include <map>
#include <algorithm>
int main(void)
{
std::map<int, std::shared_ptr<int>> map;
map[1] = std::make_shared<int>(3);
map[2] = std::make_shared<int>(5);
map[4] = std::make_shared<int>(-2);
auto it = std::find_if(map.begin(), map.end(),
[](const std::pair<int, std::shared_ptr<int>> &elem) {
std::cout << "find_if: " << elem.second.use_count() << std::endl;
return *elem.second == 5;
});
std::cout << "main: " << it->second.use_count() << std::endl;
}
通过这段代码,我得到了
的输出find_if: 2
find_if: 2
main: 1
而且我不确定引用计数增加是否是正确的行为。
我使用的是 Visual Studio 2017。
最佳答案
问题是你的lambda参数的类型
const std::pair<int, std::shared_ptr<int>> &
...这不符合 std::map<<int, std::shared_ptr<int>>>::value_type
(您缺少键类型的 const
)。
因此,为了调用您的 lambda,类型为 std::pair<int, std::shared_ptr<int>>
的临时对象必须从 std::pair<const int, std::shared_ptr<int>>
构建存储在 std::map
.
构造此对象时,shared_ptr
被复制,所以它的引用计数器必须递增。
如果将参数的类型更改为
const std::pair<const int, std::shared_ptr<int>> &
...问题消失了。您也可以使用 const auto&
而不是这里的完整类型。
1 如果您使用非 const
在这里引用,你会得到一个编译器错误,因为你不能初始化一个 std::pair<int, std::shared_ptr<int>>
类型的引用来自std::pair<const int, std::shared_ptr<int>>
,而是一个 const
-reference 允许使用临时文件。
关于c++ - 在包含 shared_ptr 的 map 上使用 find_if 会增加引用计数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56099473/