無序集合中元組的通用雜湊函數
std::unordered_map 和std::unordered_set 容器提供高效率的元素查找和插入基於它們的哈希值。但是,在不定義自訂雜湊函數的情況下使用元組作為這些集合中的鍵可能會導致意外行為。
要修正此問題,一種方法是為特定元組類型手動定義雜湊函數,例如:
template<> struct std::hash<std::tuple<int, int>> { size_t operator()(std::tuple<int, int> const& tuple) const { ... } };
雖然這種方法有效,但為每個使用的元組類型定義雜湊函數可能很乏味。要自動執行此操作,可以如下實現通用雜湊函數:
#include <tuple> namespace std { namespace { // Code derived from Boost template<class T> inline void hash_combine(std::size_t& seed, T const& v) { ... } // Recursive template code from Matthieu M. template<class Tuple, size_t Index = std::tuple_size<Tuple>::value - 1> struct HashValueImpl { ... }; } template<typename... TT> struct hash<std::tuple<TT...>> { size_t operator()(std::tuple<TT...> const& tuple) const { ... } }; }
此函數利用參數相關名稱查找(ADL) 來允許編譯器根據元組類型自動選擇正確的雜湊實現.
標準一致性解決方案
值得注意的是,在std命名空間中定義非標準函數是未定義的行為。對於符合標準的解決方案,可以建立自訂命名空間並用於定義雜湊函數:
namespace my_hash { // Forward non-tuple types to the std::hash template<typename TT> struct hash { ... }; // Provide the optimized hash for tuples template<typename... TT> struct hash<std::tuple<TT...>> { ... }; }
使用此解決方案時,無序集合必須明確引用自訂雜湊實現,如下所顯示:
unordered_set< std::tuple<double, int>, std::hash<std::tuple<double, int>>, std::equal_to<std::tuple<double, int>> > test;
以上是如何為無序集合中的元組實作通用雜湊函數?的詳細內容。更多資訊請關注PHP中文網其他相關文章!