【GaussDB】內存資源告急:深度診斷一起“memory temporarily unavailable”故障

一、背景

在客戶測試環境中(GaussDB 506.0 SPC0100 集中式),一個重度使用存儲過程的系統,頻繁出現內存臨時不可用的問題(ERROR: memory is temporarily unavailable)。令人困惑的是,這個環境配置的內存大小已經數十倍于遷移前的Oracle。


二、GaussDB提供的觀測方法

GaussDB官方產品文檔中有一個《內存過載》章節,詳細描述了在出現內存過載情況下如何定位,但似乎這個章節并沒有在官方網站上公開。下面按照本次分析過程進行描述。

內存監控視圖

GaussDB提供了幾個重要的內存視圖:

gs_total_memory_detail
顯示當前數據庫節點的內存使用情況,單位為MB。當GUC參數enable_memory_limit的值為off時,本視圖不可用。

gs_session_memory_detail
顯示會話的內存使用情況,以MemoryContext節點來統計。當開啟線程池(enable_thread_pool = on)時,該視圖包含所有線程和會話的內存使用情況。當GUC參數enable_memory_limit的值為off時,本視圖不可用。

gs_shared_memory_detail
查詢當前節點所有已產生的共享內存上下文的使用信息。

內存使用情況示例

SELECT?*?FROM?gs_total_memory_detail;

nodenamememorytypememorymbytes
primarymax_process_memory24567
primaryprocess_used_memory7847
primarymax_dynamic_memory16651
primarydynamic_used_memory1843
primarydynamic_peak_memory2942
primarydynamic_used_shrctx1286
primarydynamic_peak_shrctx1387
primarymax_backend_memory1360
primarybackend_used_memory1
primaryhigh_backend_thread_memory20
primaryhigh_backend_thread_max_memory768
primarymedium_backend_thread_memory113
primarymedium_backend_thread_max_memory1536
primarylow_backend_thread_memory0
primarylow_backend_thread_max_memory768
primarymax_shared_memory6548
primaryshared_used_memory5402
primarymax_cstore_memory16
primarycstore_used_memory0
primarymax_sctpcomm_memory0
primarysctpcomm_used_memory0
primarysctpcomm_peak_memory0
primaryother_used_memory527
primarygpu_max_dynamic_memory0
primarygpu_dynamic_used_memory0
primarygpu_dynamic_peak_memory0
primarypooler_conn_memory0
primarypooler_freeconn_memory0
primarystorage_compress_memory0
primaryudf_reserved_memory0
primaryllvm_used_memory0
primarymax_htap_memory0
primaryhtap_used_memory0


內存類型理解指南

要真實理解gs_total_memory_detail里這些內存類型的關系,并且理解gs_session_memory_detail和gs_shared_memory_detail記錄的內存對應到gs_total_memory_detail的映射關系,需要明確以下幾點:


內存指標含義


max:表示最大可以為多少,超過就會報內存不足
used:表示當前已經申請了多少
peak:表示本次數據庫啟動以來的歷史used峰值


內存分配關系


max_process_memory?是通過參數設置的
max_shared_memory主要為shared_buffers,但是這個值的大小可能會比shared_buffers要大
max_dynamic_memory是?max_process_memory - max_shared_memory - max_cstore_memory - max_backend_memory - ...?得到的
dynamic_used_memory?包括了:

動態會話內存(gs_total_memory_detail里沒列出來)
dynamic_used_shrctx
high_backend_thread_memory
medium_backend_thread_memory
low_backend_thread_memory
💡?注意:后三個high/medium/low暫時不用關心,這是新版本中引入的特性,為后臺線程專門分出來的內存。


GaussDB內存區域劃分

在GaussDB中,主要的內存區域分為:

📁 共享內存(主要為shared_buffers)
📁 動態內存(dynamic_memory)
├── 📄 動態會話內存 (gs_session_memory_detail)
├── 📄 動態共享內存 (dynamic_used_shrctx) (gs_shared_memory_detail)
└── 📄 動態后臺內存
???重要提醒:這里出現兩個"共享內存",非常容易產生理解上的歧義。比如gs_shared_memory_detail這個視圖,查的就不是"共享內存",而是"動態共享內存"。

可以這么理解:

shared_buffers主要是data buffer,即表和索引的數據
GaussDB實現的global plan cache/global plsql cache/unique sql hash table等全局緩存,并不屬于shared_buffers,而是在dynamic_used_shrctx里

內存追蹤配置

內存不足的報錯經常是一個瞬間沖高,回頭再來看這些視圖時,已經找不到對應的內存上下文,因此GaussDB在出現內存不足的報錯時,會自動把當時的內存上下文情況生成到單獨的日志文件中。

memory_trace_level?參數
參數說明:動態內存使用超過最大動態內存的90%后,記錄內存申請信息的管控等級。該參數僅在GUC參數use_workload_manager和enable_memory_limit打開時生效。

參數類型:枚舉類型

參數單位:無

取值范圍:

級別說明
none表示不記錄內存申請信息
level1動態內存使用超過最大動態內存的90%后,會記錄以下信息,并將記錄的內存信息保存在$GAUSSLOG/mem_log目錄下:
? 全局內存概況
? instance,session,thread三種類型的所有內存上下文中內存占用前20的內存上下文的內存使用情況
? 每個內存上下文的totalsize、freesize字段
level2在level1的基礎上,還會記錄每個內存上下文上所有內存申請的詳細信息,包含申請內存所在的文件,行號和大小


默認值:level1

???設置建議:該參數設置為level2后,會記錄每個內存上下文的內存申請詳情(file,line,size字段),會對性能影響較大,需慎重設置。

相關功能:

記錄的內存快照信息可以通過系統函數gs_get_history_memory_detail(cstring)查詢
記錄的內存上下文是經過將同一類型所有重名的內存上下文進行匯總之后得到的


三、現場分析

初步發現

由于默認是level1,沒有記錄申請內存的源碼文件和行號,因此后面現場調成了level2。
當時的mem_log中有記錄兩個比較可疑的內存上下文:

位置上下文名稱數量大小
shared_memoryunique sql hash table1個~8G
session_memorySRF multi-call contex1個~8G


然后回頭查gs_shared_memory_detail、gs_session_memory_detail這兩個視圖,發現的確可以查到unique sql hash table占了8G,但是查不到SRF multi-call context。

監控腳本

客戶DBA寫了個監控腳本,每隔20秒采集一下各個內存視圖的數據。

但幾天后,仍然沒有采集到SRF multi-call context,而數據庫日志中仍然會時不時報錯內存臨時不可用。

關鍵發現

在一次偶然的連續查詢gs_total_memory_detail時,發現已使用的動態內存上下波動幅度高達8GB。

于是猜想可能是一個非常短的時間產生了SRF multi-call context這個上下文,執行完后就釋放了,所以間隔20秒采一次能采到的概率非常低。

深入分析

數據庫大廠的內核研發往往都只負責各自一小塊領域,華為內核研發遠程查看日志,并沒有發現什么可疑的點,而且還拉了好幾個不同領域的內核研發,都沒有找到原因。

但是在遠程會議中,客戶快速一頁一頁翻日志時,我發現一個現象:

在出現內存臨時不可用報錯的前面一段,會頻繁打印相同格式的日志,而且中間有個數字一直在漲,從1XXXXXXXXX一直漲到7XXXXXXXXX,然后就沒有這個重復日志了。

直覺告訴我,很可能與這個有關。于是讓客戶回到這段日志前面,然后發現了類似下面的這么一行:

2025-07-25 10:00:01.523 primary RdsAdmin postgres xxx.xxx.xxx.xxx 140216907527936 12[0:0#0] 0 gsql 00000 31806672368306287 [BACKEND] LOG: ?00000: unique_sql_id=3740540431, Current SQL is consuming about 1099 MB, allocating 102921000 bytes, memctx:SRF multi-call context, appname:, user_id: 16616, current query is: select usename,count(*) from dbe_perf.statement group by usename

問題串聯

很明顯這里就出現了SRF multi-call context,然后這段日志下面就是不斷地在申請內存,直到申請了8G,后面很快就有一個業務調用存儲過程報錯內存不足了。

也就是說,在這個環境中,查詢一次dbe_perf.statement這個視圖,就會申請8G內存。這個查詢,是TPOPS端定時采集的SQL。

dbe_perf.statement這個視圖里實際上是一個查詢特定內存數據的返回多行的函數,查詢的就是unique sql hash table里的內容。

問題鏈條分析

分析到這里,感覺大部分疑點都串起來了:

由于某種原因,歸一化SQL的內存達到了8G
然后由于TPOPS定時查詢dbe_perf.statement,導致內存瞬間又消耗了8GB
光這兩個動態內存上下文就占了16GB
由于這是個重度存儲過程的系統,GLOBAL PLSQL CACHE又占了幾個GB
動態內存全用完了,導致業務會話報錯

進一步探究

歸一化內存為什么會達到8GB?

我在很早就問過華為內核研發:track_activity_query_size=40960這么設置,如果SQL沒達到這個長度,占用的內存是SQL實際的長度還是40960?

我一直記得在openGauss系數據庫中,這個內存一定是按設置的這個大小申請,不會根據SQL實際長度變化,但是華為內核研發說在GaussDB中內存占用只會按實際SQL長度來,除非SQL長度達到或者超過這個數,才會申請這么多內存。

由于GaussDB并沒有開源,所以當時我只能相信華為說的,可能GaussDB做了優化。

巧合的乘積

可是客戶現場出現這個現象時,我直接計算了下:

40,960 × 200,000 = 8,192,000,000

剛好差不多8G,這么巧合?

然后客戶也查了,實際在dbe_perf.statement里query的匯總字節數,也就只有一百多MB。

但是華為內核研發說他看了那段代碼,說的確是按實際長度來的,但是他又無法解釋這8GB到哪里去了,因為算上其他屬性的長度,每行最多就再加幾百KB。


四、問問萬能的AI

GaussDB沒開源,但是openGauss是開源的,本來想用Cursor來分析一下,奈何被斷供了,只能先用vscode的Copilot了。

打開openGauss源碼目錄,切換Copilot到agent模式,開問:

第一輪提問
Dark-Athena: 看下SRF multi-call context 這個上下文在什么時候會產生

GitHub Copilot?:內容較長具體可點擊文末左下角查看原文獲取


總結:SRF multi-call context 在任何集合返回函數第一次被調用時產生,用于在函數的多次調用之間保持狀態和數據,直到函數返回完所有結果后被清理。

第二輪提問
Dark-Athena: 分析下執行get_instr_unique_sql這個函數時,申請的"SRF multi-call context"占用大小與什么有關

GitHub Copilot: 內容較長具體可點擊文末左下角查看原文獲取

在生產環境中,建議根據實際的 SQL 多樣性和系統內存容量合理配置?instr_unique_sql_count?和?pgstat_track_activity_query_size?參數,以平衡監控精度和內存占用。

第三輪關鍵提問
Dark-Athena: 如果我一條SQL的長度沒達到pgstat_track_activity_query_size,也會申請pgstat_track_activity_query_size這個值大小的內存么?

GitHub Copilot: 內容較長具體可點擊文末左下角查看原文獲取

所以答案是肯定的:即使你的SQL很短(比如SELECT 1;),系統仍然會為每個后端進程的st_activity字段分配完整的pgstat_track_activity_query_size大小的內存空間。


五、結論分析

結合AI的分析,可以得出以下結論:

核心發現

1、固定內存分配

track_activity_query_size是固定會申請的內存大小
占用的內存大小不會由于SQL比這個值小而減小
實際單個unique sql所占用的空間,會比track_activity_query_size還要大一些
當instr_unique_sql_count為GaussDB默認的200000,track_activity_query_size為40960時,unique sql hash table能達到8GB

2、SRF函數特性

SRF函數就是返回多行的函數
dbe_perf.statement里就是一個SRF函數
為了在返回多行時保持數據穩定性,就會把查詢結果全存到內存里,直到查詢完才釋放

3、內存復制機制

dbe_perf.statement查的就是unique sql hash table的內容
SRF為了數據穩定性,幾乎把這8GB的內存復制了一份,放到了SRF multi-call context里

深層問題探究

看上去這就是個非常低級的問題?但是問題還沒完:

為什么unique sql會那么快達到200000個?

這個環境才剛部署沒幾天,而且都是跑的存儲過程,沒有什么拼接SQL,理論上SQL數是穩定有限的。

通過截取statement.query前200個字符進行group by計數排序,發現很大一部分SQL都是一個declare開頭的自治事務匿名塊。

根本原因

由于我之前和openGauss社區的研發一起分析過plsql編譯依賴這個功能的問題,當時為了解決編譯時數據字典表鎖釋放的問題,我提出了可以起個自治事務去編譯,這樣能避免長時間持有元數據鎖的問題。而GaussDB也是用的這個方案(巧合?)。

所以我一眼就看出來GaussDB里記錄的這些SQL是在做存儲過程編譯,但是GaussDB把整個存儲過程的內容都放到這個匿名塊里了,而且還有一些oid信息,因此必然是不同的SQL。

這個匿名塊還會做一些數據字典的DML操作,這些DML的SQL是固定不變的,大概有6~7條。再來就是dbe_perf.statement里,對于parent_unique_sql_id不同的同一個unique_sql_id,會視為不同的記錄。

問題鏈條完整梳理

存儲過程編譯:每次改一個存儲過程,就在dbe_perf.statement里生成了約10條的記錄
重復生成:反復改就反復生成,有時候全量存儲過程重建,數字唰唰唰就漲上去了
資源耗盡:200000也經不起這么耗,真正的業務SQL可能還會計不進去了
內存占用:全是存儲過程編譯時自動產生的這些SQL

目前客戶這邊只能先調小track_activity_query_size到4K,讓dbe_perf.statement的內存占得小些,至少讓業務測試能繼續進行下去。

六、復現方法

診斷了這么多天的問題,弄清楚原理后,非常容易復現unique sql hash table和SRF multi-call context申請大量內存的現象:

環境配置

-- 這個是單個會話的unique sql上限,由于模擬測試都在一個會話里,所以要調大

gs_guc reload -c "track_stmt_session_slot=200000"

-- 直接設置到最大值,內存漲得最快

gs_guc reload -c "track_activity_query_size=102400"

-- 重啟,釋放 unique sql 內存

gs_ctl restart

測試腳本

-- 構造不同的SQL
-- 注意GaussDB對于表別名或字段別名不同、常量不同的也會進行歸一化
-- 所以這里直接用不同的對象名

DECLAREx_sql1?text;x_sql2 text;i int;
BEGIN
FOR?i?IN1..5000
LOOPx_sql1 :=?'CREATE TABLE t_abcd'||i||'(a int);';x_sql2 := 'DROPTABLE?t_abcd'||i;EXECUTE IMMEDIATE x_sql1;EXECUTE IMMEDIATE x_sql2;END LOOP;RAISE NOTICE '%', x_sql1;
END;
/

驗證結果

-- 查詢動態共享內存里unique sql hash table的大小

SELECTcontextname,
count(1),
ROUND(sum(totalsize)/1024/1024,2)?AS?TOTALSIZE_MB,
ROUND(Sum(usedsize)/1024/1024)?AS?usedsize_MB?
FROM?GS_shared_MEMORY_DETAIL ?
GROUPBY?contextname?
ORDERBY3DESC
LIMIT10;
contextnamecounttotalsize_mbusedsize_mb
unique sql hash table11468.751469
DefaultTopMemoryContext1172.5760
ASP unique sql hash table182.1182


unique sql hash table占1個多GB
-- 查詢SQL實際長度所占的空間,和按track_activity_query_size的長度計算的空間

SELECT
sum(lengthb(query))/1024/1024AS?actual_size_mb,(count(1)*current_setting('track_activity_query_size')::int)/1024/1024AS?allocated_size_mb
FROM?dbe_perf.statement;
actual_size_mballocated_size_mb
0.381401.07


按track_activity_query_size來算,也是1個多GB。
日志驗證

執行查詢后,日志中出現SRF multi-call context:

2025-07-25 10:00:01.523 primary admin postgres 172.17.0.1 140216907527936 12[0:0#0] 0 Mogeaver 23.3.1 - SQLEditor <Script-22.sql> 00000 31806672368306287 [BACKEND] LOG: ?00000: unique_sql_id=3740540431, Current SQL is consuming about 1099 MB, allocating 102921000 bytes, memctx:SRF multi-call context, appname:, user_id: 16616, current query is: select sum( lengthb(query) )/?/?,(count(?)*current_setting(?)::int)/?/? from dbe_perf.statement
2025-07-25 10:00:01.523 primary admin postgres 172.17.0.1 140216907527936 12[0:0#0] 0 Mogeaver 23.3.1 - SQLEditor <Script-22.sql> 00000 31806672368306287 [BACKEND] LOCATION: ?mmgr_memory_check_reach_one_gb, framework_memory_memctrl_util.cpp:241
2025-07-25 10:00:01.523 primary admin postgres 172.17.0.1 140216907527936 12[0:0#0] 0 Mogeaver 23.3.1 - SQLEditor <Script-22.sql> 00000 31806672368306287 [INSTR] LOG: ?00000: [UniqueSQL] idx[10] - new memory allocated: 102921000
2025-07-25 10:00:01.523 primary admin postgres 172.17.0.1 140216907527936 12[0:0#0] 0 Mogeaver 23.3.1 - SQLEditor <Script-22.sql> 00000 31806672368306287 [INSTR] LOCATION: ?unique_sql_log_result_mem, instr_unique_sql.cpp:1407
2025-07-25 10:00:01.524 primary admin postgres 172.17.0.1 140216907527936 12[0:0#0] 0 Mogeaver 23.3.1 - SQLEditor <Script-22.sql> 00000 31806672368306287 [INSTR] LOG: ?00000: [UniqueSQL] total memory allocated: 1132131000
2025-07-25 10:00:01.524 primary admin postgres 172.17.0.1 140216907527936 12[0:0#0] 0 Mogeaver 23.3.1 - SQLEditor <Script-22.sql> 00000 31806672368306287 [INSTR] LOCATION: ?unique_sql_log_result_mem, instr_unique_sql.cpp:1408

七、總結-經驗教訓

1、經驗的積累非常重要

國產數據庫使用過程中肯定會發現很多新問題,其中有一些綜合性的問題,原廠的內核研發都不一定能找到原因,具備綜合技能的DBA能從現場的蛛絲馬跡結合長期的工作經驗所產生的直覺,來發現問題癥結所在

2、知識的積累非常重要

如果連內存區域都分不清,就算數據庫已經提供了很多方法來進行診斷,面對本文這個問題,腦子里只能是一團漿糊

3、需要學會借助AI

現在的AI有了agent,能自動且快速完成很多事,本文中就讓AI自動翻源碼分析,對問題進行了快速定位

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

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

相關文章

LeeCode 40.組合總和II

給定一個候選人編號的集合 candidates 和一個目標數 target &#xff0c;找出 candidates 中所有可以使數字和為 target 的組合。candidates 中的每個數字在每個組合中只能使用 一次 。注意&#xff1a;解集不能包含重復的組合。 示例 1:輸入: candidates [10,1,2,7,6,1,5], t…

數據結構:隊列 二叉樹

隊列&#xff08;Queue&#xff09; 是一種先進先出&#xff08;First In First Out, FIFO&#xff09; 的線性數據結構。 隊列的基本特性 1. FIFO 原則 ? 最先進入的元素最先出去 ? 就像現實生活中的排隊&#xff1a;先來的人先接受服務 2. 兩個主要操作端 ? 隊尾&#xff…

FTP工作原理及搭建實操

文章目錄前言一、FTP概述二、FTP工作原理2.1 FTP的作用與模式2.2 FTP工作流程2.2.1 主動模式&#xff08;PORT模式&#xff09;2.2.2 被動模式&#xff08;PASV模式&#xff09;2.2.3 對比表格2.2.4 如何選擇&#xff1f;2.2.5 補充&#xff1a;現代FTP服務器的常見做法三、FTP…

setup 語法糖核心要點

1. 基本語法<!-- 傳統寫法 --> <script lang"ts"> export default {setup() {let name 張三function changeName() { name 李四 }return { name, changeName }} } </script><!-- 語法糖寫法 --> <script setup lang"ts"> …

C++---多態(一個接口多種實現)

C的多態&#xff08;Polymorphism&#xff09;是面向對象編程&#xff08;OOP&#xff09;的三大核心特性之一&#xff08;另外兩個是封裝和繼承&#xff09;&#xff0c;其核心思想是一個接口&#xff0c;多種實現&#xff0c;即同一操作作用于不同對象時&#xff0c;可產生不…

【機器學習深度學習】vLLM的核心優化技術詳解

目錄 前言 一、vLLM簡介&#xff1a;為什么它如此重要&#xff1f; 二、核心技術一&#xff1a;PagedAttention — 顯存管理的革命 2.1 傳統注意力緩存的缺陷 2.2 分頁式存儲管理 三、核心技術二&#xff1a;張量并行 — 多GPU推理的基石 3.1 什么是張量并行&#xff1f…

MySQL 高級主題:索引優化、ORM 與數據庫遷移

第五部分&#xff1a;索引優化1. 為什么需要索引&#xff1f;索引是提高數據庫查詢性能的關鍵數據結構&#xff0c;它類似于書籍的目錄&#xff0c;可以幫助數據庫快速定位到所需數據&#xff0c;而不必掃描整個表。2. 索引類型主鍵索引 (PRIMARY KEY): 唯一且非空&#xff0c;…

Eplan教程:網絡與PLC

歡迎大家來到“Eplan帶你做項目”第六個過程。在第五個過程中&#xff0c;Eplan基于實際項目的繪制&#xff08;電氣設計中的電源回路以及電源分配相關回路&#xff09;重點分享分了“電機的供電和控制圖紙的繪制”。本文中&#xff0c;先猜個問題&#xff0c;設計一個PLC系統&…

大模型落地全攻略:從技術實現到場景應用

大語言模型&#xff08;LLM&#xff09;的快速發展正在重塑各行各業的智能化進程&#xff0c;但其落地應用仍面臨技術適配、場景融合、成本控制等多重挑戰。本文將系統解析大模型落地的四大核心方向 ——微調技術、提示詞工程、多模態應用和企業級解決方案&#xff0c;通過代碼…

【論文】Zotero文獻管理

Zotero文獻管理 寫論文前查找閱讀大量文獻&#xff0c;寫論文時引用文獻&#xff0c;都是一件非常麻煩的事情&#xff0c;一款合適的文獻管理工具可以幫助我們更快捷地完成這些任務。zotero作為一款免費開源的工具&#xff0c;可以實現文獻閱讀、同步管理以及引用管理。 安裝…

MsSQL 函數,實現數字轉換成人民幣大寫

MsSQL 函數&#xff0c;實現數字轉換成人民幣大寫-- 如果函數已存在則刪除 IF OBJECT_ID(dbo.ConvertToRMBChineseNew, FN) IS NOT NULLDROP FUNCTION dbo.ConvertToRMBChineseNew GOCREATE FUNCTION dbo.ConvertToRMBChineseNew (NumberInput SQL_VARIANT -- 使用 SQL_VARIANT…

OpenHarmony深度定制:從系統到模塊的全景剖析與自定義模塊實戰

摘要:OpenHarmony 作為面向萬物互聯時代的開源操作系統,其“系統-子系統-部件-模塊”的四層架構設計,為開發者提供了高度可裁剪、可擴展的能力。本文將系統梳理這四層結構的職責邊界與協作關系,并手把手演示如何向 OpenHarmony 新增一個可交付的自定義模塊(Module),幫助…

數字社會學是干什么的?數字社會學理論與數字社會學家唐興通講數字社會學書籍有哪些?AI社會學人工智能社會學理論框架

在當今社會&#xff0c;傳統物理空間和人際關系網絡成為了許多年輕人尋找合適伴侶的重大障礙。以深圳為例&#xff0c;這座移民城市的大部分居民都來自外地&#xff0c;年輕人的人脈關系、尤其是親戚關系大多仍在家鄉。這使得深圳的單身男女在交友和婚戀方面的選擇面變得狹窄&a…

數據庫-MYSQL配置下載

目錄 一.數據庫概念 一、數據庫的基本定義 二、數據庫管理系統&#xff08;DBMS&#xff09; 三、數據庫系統&#xff08;DBS&#xff09; 四、數據模型 五、數據庫的特點 六、數據庫的應用領域 二.MySql 一、開源免費&#xff0c;降低中大型項目成本 二、跨平臺與兼容…

Java 中表示數據集的常用集合類

Java 中表示數據集的常用集合類 Java 集合框架提供了多種數據結構來表示和操作數據集&#xff0c;每種集合類都有其特定的用途和性能特征。以下是主要的集合類及其特點&#xff1a; 一、List 接口及其實現類 1. ArrayList 特點&#xff1a;基于動態數組實現優點&#xff1a;隨機…

Django REST框架核心:GenericAPIView詳解

Django REST framework (DRF) 中 GenericAPIView 的源碼核心部分。 它是所有“泛型視圖”的基礎類&#xff0c;比如常用的 ListAPIView、RetrieveAPIView、CreateAPIView 都是繼承自它。&#x1f31f; 作用繼承自 APIView&#xff0c;因此仍然是一個標準的 DRF 視圖。提供了常用…

深入解析HashMap的存儲機制:擾動函數、哈希計算與索引定位

今天復習了一下HashMap的部分&#xff0c;寫一篇博客記錄一下今天學習內容雖然之前學習過&#xff0c;但由于后來沒怎么使用過而且也沒復習基本忘得差不多了在Java的HashMap中&#xff0c;高效存儲鍵值對的核心在于哈希算法和索引定位。本文將結合源碼逐步拆解存儲流程&#xf…

【機器學習 / 深度學習】基礎教程

階段一&#xff1a;機器學習 / 深度學習基礎教程定位&#xff1a;針對準備進入 AI多智能體開發 的初學者&#xff0c;打牢機器學習與深度學習的基礎。一、為什么需要學習機器學習/深度學習 在進入智能體&#xff08;Agent&#xff09;開發之前&#xff0c;必須具備一定的 機器學…

ESP32應用——HTTP client(ESP-IDF框架)

目錄 一、前言 二、URL 2.1 URL簡介 2.2 URL示例 三、HTTP 3.1 HTTP協議概述 3.2 HTTP的工作原理 3.2.1 HTTP 請求-響應流程 3.2.2 HTTP 請求結構 3.2.3 HTTP請求方法 3.2.4 HTTP響應結構 3.2.5 HTTP狀態碼 四、ESP HTTP 客戶端流程 五、ESP HTTP 客戶端實戰解析…

動學學深度學習07-現代卷積神經網絡

動學學深度學習pytorch 參考地址&#xff1a;https://zh.d2l.ai/ 文章目錄動學學深度學習pytorch1-第07章-現代卷積神經網絡1. AlexNet1.1 AlexNet 的核心貢獻是什么&#xff1f;1.2 AlexNet 與 LeNet 的主要區別有哪些&#xff1f;1.3 為什么 AlexNet 需要 GPU 訓練&#xff1…