MySQL 慢 SQL 識別與優化

一、識別慢 SQL

1. 啟用慢查詢日志

-- 查看當前慢查詢配置
SHOW VARIABLES LIKE 'slow_query%';
SHOW VARIABLES LIKE 'long_query_time';-- 開啟慢查詢日志(臨時生效)
SET GLOBAL slow_query_log = 'ON';
SET GLOBAL long_query_time = 2;  -- 設置慢查詢閾值(秒)
SET GLOBAL slow_query_log_file = '/var/lib/mysql/slow.log';-- 記錄未使用索引的查詢
SET GLOBAL log_queries_not_using_indexes = 'ON';-- 永久生效需修改 my.cnf
[mysqld]
slow_query_log = 1
slow_query_log_file = /var/lib/mysql/slow.log
long_query_time = 2
log_queries_not_using_indexes = 1
查看慢查詢日志內容:使用系統命令查看日志文件(Linux)

假設你的日志文件在 /var/lib/mysql/slow.log,可以直接用 tailcatless 查看:

tail -f /var/lib/mysql/slow.log   # 實時查看新增的日志
cat /var/lib/mysql/slow.log       # 查看全部內容
less /var/lib/mysql/slow.log      # 分頁查看

示例日志格式如下:

# Time: 2025-06-20T17:30:45.123456Z
# User@Host: root[root] @ localhost []
# Query_time: 3.123456  Lock_time: 0.000000 Rows_sent: 1  Rows_examined: 1000000
SET timestamp=1750486245;
SELECT * FROM users WHERE username = 'test';
  • Query_time: 查詢耗時(秒),超過?long_query_time?才會被記錄。
  • Rows_examined: 掃描行數,越大越可能需要優化。
  • SQL語句: 實際執行的 SQL。

2. 使用性能分析工具

-- 查看當前運行中的慢查詢
SHOW FULL PROCESSLIST;-- 使用 EXPLAIN 分析執行計劃
EXPLAIN SELECT * FROM orders WHERE customer_id = 1000;-- 使用 EXPLAIN ANALYZE(MySQL 8.0+)
EXPLAIN ANALYZE SELECT * FROM products WHERE price > 100;-- 性能分析(臨時啟用)
SET profiling = 1;
SELECT * FROM large_table;
SHOW PROFILES;
SHOW PROFILE FOR QUERY 1;

3.使用?EXPLAIN?分析 SQL 執行計劃的詳細指南

基礎用法(直接在 SQL 前加?EXPLAIN
EXPLAIN SELECT * 
FROM orders 
WHERE user_id = 100 AND status = 'completed' 
ORDER BY created_at DESC 
LIMIT 10;

輸出結果示例及關鍵列解析:

idselect_typetablepartitionstypepossible_keyskeykey_lenrefrowsfilteredExtra
1SIMPLEordersNULLrefidx_user_ididx_user4const50010.00Using where; Using filesort

核心列深度解析:
  1. type(訪問類型)?-?最重要指標

    • 性能排序:system?>?const?>?eq_ref?>?ref?>?range?>?index?>?ALL

    • 優化目標:至少達到?range?級別,避免?ALL(全表掃描)

    • 示例診斷:ref?表示使用了非唯一索引? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?

  2. key(實際使用索引)

    • 檢查是否使用預期索引:idx_user(實際使用) vs?idx_user_status(可能更好的索引)

    • 若為?NULL?表示未使用索引 → 需優化

  3. rows(掃描行數)

    • 預估掃描 500 行 → 結合?filtered?列,實際返回約 500 × 10% = 50 行

    • 目標:減少該值

  4. Extra(額外信息)?-?問題高發區

    • Using filesort:手動文件排序(需優化)

    • Using temporary:創建臨時表(需優化)

    • Using index:覆蓋索引(好現象)

    • Using where:存儲引擎返回后再次過濾

類型 (type)性能排序含義描述典型場景掃描方式掃描行數是否用索引優化建議
system★★★★★ 最佳系統表/僅有一行記錄? MyISAM/Inemory引擎的單行系統表
? 衍生表只有一行數據
直接訪問系統記錄1?無需優化
const★★★★☆ 極優主鍵/唯一索引的單行訪問??WHERE id = 1?(主鍵查詢)
??WHERE unique_col = 'value'?(唯一索引)
常量掃描
直接定位單行
1?確保主鍵/唯一索引有效
eq_ref★★★★☆ 極優主鍵關聯查詢
(多表JOIN時)
??JOIN ... ON t1.primary_key = t2.primary_key
? 驅動表每行匹配被驅動表主鍵
唯一索引掃描
每行只匹配一次
1/N
(N=驅動表行數)
?確保JOIN字段是主鍵或唯一索引
ref★★★☆☆ 良好非唯一索引的等值查詢??WHERE index_col = 'value'
? 普通索引關聯查詢
? 最左前綴匹配查詢
索引范圍掃描
可能返回多行
N
(匹配行數)
?提升索引選擇性
添加組合索引
range★★☆☆☆ 中等索引范圍掃描??WHERE id > 100
??BETWEEN 100 AND 200
??IN (1,2,3)
??LIKE 'prefix%'
索引部分掃描
指定范圍內遍歷
M
(范圍行數)
?控制掃描行數<1萬
避免大范圍掃描
index★☆☆☆☆ 較差全索引掃描??SELECT indexed_col FROM table?(覆蓋索引)
??ORDER BY indexed_col?(無WHERE條件)
? 索引全掃描
遍歷整個索引樹
不讀數據文件
全索引
(索引條目數)
?確認是否需回表
檢查排序必要性
ALL?? 最差全表掃描? 無索引字段查詢:WHERE non_index_col=...
? 前導通配符:LIKE '%value%'
? 未優化的JOIN條件
逐行掃描數據文件
性能災難
全表
(數據行數)
?緊急優化!
? 添加索引
? 重寫SQL
? 限制結果集

?通過?EXPLAIN?分析后,若出現?ALL?或?index?且掃描行數>1000,需優化

  1. 優先關注?type?避免全表掃描

  2. 重點檢查?Extra?消除警告項

  3. 通過?rows?評估執行成本

  4. 結合?key_len?判斷索引利用率

  5. 每次優化后必須重新執行 EXPLAIN 驗證效果

二、慢 SQL 的常見原因

1. 索引問題

-- 缺失索引
SELECT * FROM users WHERE last_name = 'Smith'; -- 無索引-- 索引失效
SELECT * FROM orders WHERE YEAR(order_date) = 2023; -- 函數導致索引失效

2. 全表掃描

-- 未使用索引導致全表掃描
SELECT * FROM products WHERE category LIKE '%electronics%';

3. 復雜 JOIN

-- 多表 JOIN 未優化
SELECT * 
FROM orders o
JOIN customers c ON o.customer_id = c.id
JOIN products p ON o.product_id = p.id
WHERE c.country = 'USA' AND p.price > 100;

4. 大表分頁

-- 低效的分頁查詢
SELECT * FROM logs ORDER BY id LIMIT 1000000, 20;

5.低效子查詢

-- 低效的子查詢
SELECT * FROM orders 
WHERE customer_id IN (SELECT id FROM customers WHERE country = 'China'
);

?三、慢 SQL 優化方案

1. 索引優化策略

-- 添加必要索引
CREATE INDEX idx_last_name ON users(last_name);
CREATE INDEX idx_order_date ON orders(order_date);-- 使用覆蓋索引
SELECT customer_id, order_date FROM orders; -- 建立 (customer_id, order_date) 索引-- 索引合并優化
SELECT * FROM products 
WHERE category_id = 5 OR price > 100; -- 分別建立兩個索引-- 強制索引使用
SELECT * FROM orders FORCE INDEX (idx_order_date) 
WHERE order_date BETWEEN '2023-01-01' AND '2023-01-31';

2. SQL 重寫

-- 避免 SELECT * 
SELECT id, name, email FROM users;-- 分頁優化
SELECT * FROM logs WHERE id > 1000000 ORDER BY id LIMIT 20;-- JOIN 優化
SELECT o.id, c.name, p.product_name 
FROM orders o
FORCE INDEX (idx_customer) 
JOIN customers c ON o.customer_id = c.id
JOIN products p ON o.product_id = p.id
WHERE c.country = 'USA';-- 子查詢轉 JOIN
SELECT o.* 
FROM orders o
JOIN customers c ON o.customer_id = c.id
WHERE c.country = 'China';-- 避免函數操作
SELECT * FROM orders 
WHERE order_date >= '2023-01-01' 
AND order_date < '2023-02-01';

3. 表結構優化

數據庫分庫分表:垂直拆分/水平拆分

4. 架構級優化

  • 讀寫分離:寫操作到主庫,讀操作到從庫

  • 緩存層:使用 Redis 緩存熱點數據

  • 搜索引擎:復雜查詢使用 Elasticsearch

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

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

相關文章

墨記APP:水墨風記事,書寫生活詩意

在快節奏的現代生活中&#xff0c;記錄生活的點滴成為了一種獨特的儀式感。無論是日常的瑣事、突發的靈感&#xff0c;還是對未來的規劃&#xff0c;一款好用的記事軟件都能幫助我們更好地整理思緒&#xff0c;留住美好瞬間。墨記APP正是一款兼具美學與實用性的記事軟件&#x…

龍芯7A1000橋片數據手冊解讀(時序)

RTC是電池&#xff0c;理論上一直是有電的&#xff0c;圖示指的是接上220V電之后切換為系統的電。順序是這樣的&#xff1a;接上220V電之后系統的12V供電就有了&#xff0c;12V轉為5VSB&#xff0c;5VSB供給RTC3V&#xff0c;此時RTC3V轉為系統供電而不是電池供電。這里的5VSB指…

無人機氣壓計模塊技術解析

一、運行方式 1. 基礎原理 氣壓計通過測量大氣壓力間接計算高度。無人機飛行中&#xff0c;氣壓隨高度上升而降低&#xff0c;傳感器將壓力信號轉為電信號&#xff0c;經ADC轉換為數字值。 2. 工作流程 數據采集&#xff1a;同步獲取壓力與溫度值。 原始數據處理&…

第十四節:第三部分:IO流:前置知識-什么是方法遞歸以及遞歸的形式、遞歸算法三要素

什么是方法遞歸以及遞歸的形式 遞歸算法三要素 代碼 代碼一&#xff1a;認識一下遞歸的形式 package com.itheima.Recurtion; //目標:認識一下遞歸的形式 public class RecurtionTest1 {public static void main(String[] args) {test2();}//直接方法遞歸public static void…

論文閱讀筆記:Digging Into Self-Supervised Monocular Depth Estimation

論文閱讀筆記&#xff1a;Digging Into Self-Supervised Monocular Depth Estimation 1 背景2 創新點3 方法4 模塊4.1 自監督訓練4.2 優化自監督深度估計4.2.1 每個像素的最小重建損失4.2.2 自動掩碼靜態像素4.2.3 多尺度估計4.2.4 最終的訓練損失 4.3 額外考慮 5 效果 1 背景 …

YAML 數據格式詳解

1. YAML 概念 YAML (YAML Ain’t Markup Language) 是一種人性化的數據序列化格式&#xff1a; 專注于數據而非標記&#xff08;與 XML 不同&#xff09;使用簡潔的語法表示復雜數據結構可讀性高&#xff0c;適合人類編寫和閱讀廣泛應用于配置文件&#xff08;如 Docker Comp…

react擴展

首先補充一下上個章節的一點結尾內容。reducer是一個純函數&#xff0c;純函數指的是當我們在redux里面定義了我們需要共享的對象后&#xff0c;我們是不可以對共享的對象本身進行改變的。我們在獲取更新后的共享數據時&#xff0c;要去重新定義一個新的變量來獲取更新后的共享…

6.獲取圖片灰度與縮放

目錄 一、Halcon 1. 獲取像素坐標以及灰度 2. 拖動縮放 3.圖像縮放的實現方式 二、VS聯合編程 1.獲取像素坐標和灰度 2.拖動縮放 一、Halcon 1. 獲取像素坐標以及灰度 *1. 獲取像素坐標 * 1. get_mposition * 2. halcon窗口事件自帶坐標數據 * *2. 獲取像素灰度 *…

無人機+AI:革新集裝箱箱號識別的智能解決方案

在現代化物流體系中&#xff0c;集裝箱箱號識別是貨物追蹤與管理的核心環節。然而&#xff0c;傳統的人工巡檢或固定攝像頭識別方式存在效率低、覆蓋范圍有限、易受環境干擾等問題&#xff0c;難以滿足日益增長的物流需求。基于無人機與AI技術的集裝箱箱號識別系統&#xff0c;…

一種新的參數高效微調方法-LoRI

論文&#xff1a;LoRI: Reducing Cross-Task Interference in Multi-Task Low-Rank Adaptation LoRA 具體參考 1. 引言與背景&#xff1a;為什么需要 LoRI&#xff1f; 這篇論文提出了一種新的參數高效微調&#xff08;PEFT&#xff09;方法&#xff0c;名為 LoRA with Reduce…

Go網絡編程:基于TCP的網絡服務端與客戶端

Go 語言的 net 包為網絡編程提供了簡潔高效的接口。我們可以使用它快速構建 TCP 網絡服務&#xff0c;如聊天服務器、RPC、微服務通信等。 一、TCP簡介 TCP&#xff08;Transmission Control Protocol&#xff09;是面向連接的、可靠的傳輸協議&#xff0c;通信模型為客戶端-服…

【StarRocks系列】架構、核心概念

目錄 一、架構&#xff1a;分布式 MPP 列式存儲 向量化引擎 二、存儲&#xff1a;高性能列式存儲引擎 三、表設計&#xff1a;三類模型適配不同場景 四、數據寫入&#xff1a;多種方式支持實時與批量 五、數據讀取&#xff1a;極致優化的查詢引擎 總結&#xff1a;Star…

從源碼到生產:Apache 2.4.57 自動化安裝實戰指南(附腳本)

引言&#xff1a;為何選擇源碼安裝 Apache&#xff1f; 在服務器運維場景中&#xff0c;源碼編譯安裝 Apache HTTP Server 是實現精細化配置的重要方式。相比包管理器安裝&#xff0c;源碼安裝可自定義模塊組合、適配特定依賴環境&#xff0c;并精確控制版本。本文將通過自動化…

iOS開發中的安全實踐:如何通過Ipa混淆與加固確保應用安全

隨著移動應用技術的不斷發展&#xff0c;開發者越來越重視應用的安全性&#xff0c;尤其是iOS應用。無論是面對大規模的數據泄露問題&#xff0c;還是在應用上線后避免被逆向破解&#xff0c;開發者們都需要采取一系列技術手段來保護應用。然而&#xff0c;很多開發者在應用開發…

JAVA實戰開源項目:智慧生活商城系統 (Vue+SpringBoot) 附源碼

本文項目編號 T 245 &#xff0c;文末自助獲取源碼 \color{red}{T245&#xff0c;文末自助獲取源碼} T245&#xff0c;文末自助獲取源碼 目錄 一、系統介紹二、數據庫設計三、配套教程3.1 啟動教程3.2 講解視頻3.3 二次開發教程 四、功能截圖五、文案資料5.1 選題背景5.2 國內…

GNU Octave 基礎教程(8):GNU Octave 常用數學函數

目錄 一、基本算術運 二、初等數學函數 三、三角函數與反三角函數 四、統計函數 五、復數與其他函數 ? 小結 &#x1f51c; 下一講預告 GNU Octave 內置了大量數學函數&#xff0c;涵蓋初等數學、線性代數、復數運算、統計函數等&#xff0c;非常適合科研、工程計算使用…

Go語言中的文件與IO:JSON、CSV、XML處理

在數據交換與存儲中&#xff0c;JSON、CSV、XML 是常見格式。Go 標準庫為這些格式提供了強大且易用的支持&#xff0c;涵蓋結構體映射、讀寫文件、編碼解碼等操作。 一、JSON處理&#xff08;encoding/json&#xff09; 1. 基本使用&#xff1a;結構體 <-> JSON type U…

三種語言寫 MCP

參考 https://zhuanlan.zhihu.com/p/1915029704936760261 https://www.5ee.net/archives/tmXJAgWz https://github.com/modelcontextprotocol/python-sdk https://github.com/modelcontextprotocol/typescript-sdk https://modelcontextprotocol.io/quickstart/server https:/…

Python訓練營-Day38-Dataset和Dataloader類

在遇到大規模數據集時&#xff0c;顯存常常無法一次性存儲所有數據&#xff0c;所以需要使用分批訓練的方法。為此&#xff0c;PyTorch提供了DataLoader類&#xff0c;該類可以自動將數據集切分為多個批次batch&#xff0c;并支持多線程加載數據。此外&#xff0c;還存在Datase…

SVN上傳代碼

SVN&#xff08;Subversion&#xff09;是一個常用的版本控制系統&#xff0c;提供了對代碼管理和協作的支持。以下是SVN常見操作&#xff08;如獲取代碼、上傳代碼、合并沖突處理等&#xff09;的命令行流程及實例&#xff1a; 1. 獲取代碼&#xff08;Checkout&#xff09; 在…