简体   繁体   English

C++ 11 将自定义 hash function 传递到 unordered_map

[英]C++ 11 passing custom hash function into unordered_map

I am not sure I understand why this compiles.我不确定我理解为什么会这样编译。

#include <iostream>
#include <iterator>
#include <string>
#include <unordered_map>
#include <utility>
#include <vector>
#include <unordered_set>
#include <algorithm>
#include <queue>
using namespace std;



void thing() {
    auto hash = [](const std::pair<int, int> &pair) {
        return std::hash<string>()(to_string(pair.first));
    };
    auto map = std::unordered_map<std::pair<int, int>, int, decltype(hash)>();
}


int main() {

}

I haven't passed the hash function into the constructor -- how does it know the implementation to hash a pair?我还没有将 hash function 传递给构造函数——它怎么知道 hash 的实现?

It may compile because the lambda expression's type is an anonymous class - which can be instantiated (but see note below).它可以编译,因为 lambda 表达式的类型是匿名 class - 可以实例化(但请参见下面的注释)。 The code block is that class' operator()() method.代码块是该类的operator()()方法。 This class is instantiated as a default parameter value by the constructor std::unordered_map - using the lambda expression's type, which is a template argument:此 class 由构造函数std::unordered_map实例化为默认参数值 - 使用 lambda 表达式的类型,这是一个模板参数:

unordered_map( InputIt first, InputIt last,
               size_type bucket_count = /*implementation-defined*/,
               const Hash& hash = Hash(), /* <<<< INSTANTIATION HAPPENS HERE */
               const key_equal& equal = key_equal(),
               const Allocator& alloc = Allocator() );

For more on the nature of lambda expressions, see this SO question:有关 lambda 表达式性质的更多信息,请参阅此 SO 问题:

What is a lambda expression in C++11? C++11 中的 lambda 表达式是什么?


Note: As commenters note, your code doesn't actually compile with C++11 , because the implicit default constructor for the anonymous class defined by a lambda expression is deleted in C++11. Note: As commenters note, your code doesn't actually compile with C++11 , because the implicit default constructor for the anonymous class defined by a lambda expression is deleted in C++11. This has been changed in C++20: Non-capturing lambdas get a default constructor, so now the code does compile.这在 C++20 中已更改:非捕获 lambda 获取默认构造函数,因此现在代码可以编译。

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

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