C++ 容器——unordered_xxx

? ? ? ?自 C++11 開始,STL 引入了基于 hash table 的?unordered_setunordered_map 等容器,正如其名它們是無序容器。一定數量(據說有測試數據是10000000)元素時無序容器的性能要比對應的有序容器優。

一、容器數據結構

????????unordered_set、unordered_map 等容器的 Hash Table(哈希表/散列表)結構通常是:桶(bucket) + 線性表,bucket 一般用 vector 實現,線性表通常采用鏈表。當插入元素時通過哈希函數計算其哈希值,以哈希值作為 vector 的下標索引,取得元素要插入的鏈表頭,把元素插入進去。也就是說通過 鏈地址法(Separate Chaining)? 解決哈希沖突。

二、哈希函數

? ? ? ? 哈希函數是這些容器的核心,也是保證它們高性能的關鍵。C++11 為基本類型:int、float、double、char、string 提供了哈希函數。?但是要在這些容器中添加自定義類型的元素就必須提供特定的哈希函數

無自定義類的哈希函數

無論是 clang++、還是 g++ 都無法正確如下代碼,原因就是:缺失計算 Person?哈希值的函數

#include <string>
#include <unordered_set>class Person {
public:Person(const std::string &name, int age) : _name(name), _age(age) {}private:std::string _name;int         _age;
};int main(int argc, char *argv[]) {std::unordered_set<Person> persons;
}
為自定義類添加哈希函數

查看?unordered_set 的聲明、?g++ 的 /usr/include/c++/9/bits/functional_hash.h 可知:

  • unordered_set 的模板參數 Hash 默認設置為 std::hash<Key>,std::hash 是一個類模板;
  • 通過特化 std::hash,支持了諸如 int、double 基本類型的哈希函數;
  • 每個特化版本中重載了函數調用運算符
template<class Key,class Hash = std::hash<Key>,class KeyEqual = std::equal_to<Key>,class Allocator = std::allocator<Key>
> class unordered_set;/// Explicit specialization for int.
_Cxx_hashtable_define_trivial_hash(int)/// Explicit specialization for bool.
_Cxx_hashtable_define_trivial_hash(bool)/// Explicit specialization for char.
_Cxx_hashtable_define_trivial_hash(char)#define _Cxx_hashtable_define_trivial_hash(_Tp) 	\template<>						\struct hash<_Tp> : public __hash_base<size_t, _Tp>  \{                                                   \size_t                                            \operator()(_Tp __val) const noexcept              \{ return static_cast<size_t>(__val); }            \};

綜述為 Person 類定義函數對象類實現哈希函數功能

#include <string>
#include <unordered_set>struct Person {Person(const std::string &name, int age) : _name(name), _age(age) {}std::string _name;int         _age;
};struct PersonHash
{size_t operator()(const Person &person) const noexcept{return static_cast<size_t>(person._age + person._name.length());}
};int main(int argc, char *argv[]) {std::unordered_set<Person, PersonHash> persons;persons.insert({"yaoyuan", 30});}
為自定義類添加哈希函數

未完...

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/98275.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/98275.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/98275.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

分布式常見面試題整理

一、分布式理論&#xff1a; CAP理論 分布式系統最多同時滿足一致性&#xff08;C&#xff09;、可用性&#xff08;A&#xff09;、分區容錯性&#xff08;P&#xff09;中的兩個&#xff0c;無法三者兼得。 BASE理論 對CAP中一致性和可用性的權衡&#xff0c;強調基本可用&a…

Python基礎入門常用198英語單詞詳解

最近&#xff0c;我總結了一份Python學習者入門常用單詞表&#xff0c;列出了Python學習中常見的198個高頻單詞&#xff0c;供初學者學習使用。 這些單詞都比較簡單&#xff0c;非常易于理解&#xff0c;在掌握好單詞的基礎上&#xff0c;再去學Python可以達到事半功倍的效果。…

EP-SPY 網路追蹤規避實驗:山脈通聯測試

EP-SPY V3.0 https://github.com/MartinxMax/ep-spy 基於 GI6E 編碼的無線電通信工具&#xff0c;用於保護您的隱私。 https://github.com/MartinxMax/gi6e 編寫了偽協議以防止內容被解密無法通過網絡追蹤&#xff0c;抵抗官方監控無線音頻廣播&#xff0c;用於隱蔽信息傳輸…

蘋果 FoundationModels 秘典俠客行:隱私為先的端側 AI 江湖

引子 話說俠客島之上&#xff0c;有一對年輕俠侶 ——「青鋒劍客」凌云與「素心仙子」蘇凝&#xff0c;二人自幼習武&#xff0c;尤擅拆解各路奇功秘籍。 近日聽聞蘋果谷&#xff08;Apple&#xff09;于 WWDC 2025 武林大會之上&#xff0c;亮出一門全新絕學「FoundationMod…

華為基于IPD的產品質量計劃模板

目錄 模板:產品質量計劃模板....................................... 1 1. 介紹...................................................................... 5 1.1. 范圍和目的.................................................... 5 1.2. 參考資料..…

事務管理的選擇:為何 @Transactional 并非萬能,TransactionTemplate 更值得信賴

在 Spring 生態的后端開發中&#xff0c;事務管理是保障數據一致性的核心環節。開發者常常會使用 Transactional 注解快速開啟事務&#xff0c;一行代碼似乎就能解決問題。但隨著業務復雜度提升&#xff0c;這種“簡單”的背后往往隱藏著難以察覺的隱患。本文將深入剖析 Spring…

CodePerfAI體驗:AI代碼性能分析工具如何高效排查性能瓶頸、優化SQL執行耗時?

前陣子幫同事排查用戶下單接口的性能問題時&#xff0c;我算是真切感受到 “找性能瓶頸比寫代碼還磨人”—— 接口偶爾會突然卡到 3 秒以上&#xff0c;查日志只看到 “SQL 執行耗時過長”&#xff0c;但具體是哪個查詢慢、為什么慢&#xff0c;翻了半天監控也沒頭緒&#xff0…

《sklearn機器學習——繪制分數以評估模型》驗證曲線、學習曲線

估計器的偏差、方差和噪聲 每一個估計器都有其優勢和劣勢。它的泛化誤差可以分解為偏差、方差和噪聲。估計器的偏差是不同訓練集的平均誤差。估計器的方差表示對不同訓練集&#xff0c;模型的敏感度。噪聲是數據的特質。 在下圖中&#xff0c;可以看見一個函數 f(x)cos?32πxf…

2025年AI PPT必修課-匯報中AI相關內容的“陷阱”與“亮點”

《2025年AI PPT必修課-匯報中AI相關內容的“陷阱”與“亮點”》 (適用于方案匯報、戰略PPT、標書/投資人演示)一、內容類坑&#xff08;戰略/趨勢層面&#xff09;? Pitfall (不要寫)? Correct Expression (推薦寫法)Why (原因)還在強調 Caffe / Theano / TF1.x / LSTM采用 P…

Java數據結構 - 順序表模擬實現與使用

目錄1.順序表的基本介紹2.順序表的模擬實現2.1 常見的功能2.2 基本框架2.3 方法的實現2.3.1 add方法2.3.2 size方法2.3.3 display方法2.3.4 add&#xff08;int pos&#xff0c;E data)方法2.3.5 remove方法2.3.6 get方法2.3.7 contain方法2.3.8 indexOf方法2.3.9 set方法2.3.1…

rust語言 (1.88) egui (0.32.1) 學習筆記(逐行注釋)(二十六)windows平臺運行時隱藏控制臺

1、主程序第一句添加&#xff1a; 必須放在所有代碼第一句 #![cfg_attr(windows, windows_subsystem "windows")]2、 編譯命令&#xff1a;cargo build --release3、 編譯完成后運行可執行文件&#xff1a; 項目目錄/target/release/項目名.exe

什么是靜態住宅IP 跨境電商為什么要用靜態住宅IP

靜態住宅IP的定義靜態住宅IP是指由互聯網服務提供商&#xff08;ISP&#xff09;分配給家庭用戶的固定IP地址。與動態IP不同&#xff0c;靜態IP不會頻繁變動&#xff0c;長期保持穩定。其特點包括&#xff1a;固定性&#xff1a;IP地址長期不變&#xff0c;適合需要穩定網絡環境…

RabbitMQ 初步認識

目錄 1. 基本概念 2. RabbitMq 的工作流程 3. 協議 4. 簡單的生產者, 消費者模型 4.1 我們先引入 rabbitmq 的依賴 4.2 生產者 4.3 消費者 1. 基本概念 Pruducer : 生產者, 產生消息Consumer : 消費者, 消費消息Broker : RabbitMq Server, 用來接收和發送消息Connectio…

Redis(46) 如何搭建Redis哨兵?

搭建 Redis 哨兵&#xff08;Sentinel&#xff09;集群&#xff0c;確保 Redis 服務具有高可用性。以下是詳細的步驟&#xff0c;從 Redis 安裝、配置主從復制到配置和啟動 Sentinel 集群&#xff0c;并結合相關的代碼示例。 步驟 1&#xff1a;安裝 Redis 首先&#xff0c;需要…

Grafana 多指標相乘

PromQL中多指標相乘 PromQL表達式&#xff1a; 0.045 * h9_daily_income{coin"nock"} * h9_pool_price_cny{coin"nock"}&#x1f4c8; 基礎&#xff1a;單指標運算 常數與指標相乘 在PromQL中&#xff0c;常數與指標的乘法是最簡單的運算&#xff1a; # ?…

【微服務】springboot3 集成 Flink CDC 1.17 實現mysql數據同步

目錄 一、前言 二、常用的數據同步解決方案 2.1 為什么需要數據同步 2.2 常用的數據同步方案 2.2.1 Debezium 2.2.2 DataX 2.2.3 Canal 2.2.4 Sqoop 2.2.5 Kettle 2.2.6 Flink CDC 三、Flink CDC介紹 3.1 Flink CDC 概述 3.1.1 Flink CDC 工作原理 3.2 Flink CDC…

分布式數據架構

分布式數據架構是一種將數據分散存儲在多臺獨立計算機&#xff08;節點&#xff09;上&#xff0c;并通過網絡協調工作的系統設計。其核心目標是解決海量數據處理、高并發訪問、高可用性及可擴展性等傳統集中式數據庫難以應對的挑戰。以下是關鍵要點解析&#xff1a;一、核心原…

Spark 中spark.implicits._ 中的 toDF和DataFrame 類本身的 toDF 方法

1. spark.implicits._ 中的 toDF&#xff08;隱式轉換方法&#xff09;本質這是一個隱式轉換&#xff08;implicit conversion&#xff09;&#xff0c;通過 import spark.implicits._ 被引入到作用域中。它的作用是為本地 Scala 集合&#xff08;如 Seq, List, Array 等&#…

如何在MacOS上卸載并且重新安裝Homebrew

Homebrew是一款針對macOS操作系統的包管理工具&#xff0c;它允許用戶通過命令行界面輕松安裝、升級和管理各種開源軟件包和工具。Homebrew是一個非常流行的工具&#xff0c;用于簡化macOS系統上的軟件安裝和管理過程。一、卸載 Homebrew方法1&#xff1a;官方卸載腳本&#xf…

如何簡單理解狀態機、流程圖和時序圖

狀態機、流程圖和時序圖都是軟件工程中用來描述系統行為的工具&#xff0c;但它們像不同的“眼鏡”一樣&#xff0c;幫助我們從不同角度看問題。下面用生活比喻來簡單理解思路&#xff1a;狀態機&#xff1a;想象一個交通信號燈。它總是在“紅燈”“黃燈”“綠燈”這些狀態之間…