萬盛學電腦網

您现在的位置: 萬盛學電腦網 >> 程式設計 >  >> 資料庫 >> MySQL 教學

MySQL 慢查詢日志啟用、閾值設置與 EXPLAIN 執行計劃深度解析

慢查詢日志是 SQL 調優的「體檢報告」。本文詳細講解 long_query_time 動態調整、配置文件持久化啟用、5.0/5.5+ 版本差異、EXPLAIN 輸出各列含義、典型執行計劃模式識別,讓你從「感覺慢」進化到「數據驅動優化」。

慢查詢閾值配置

查看當前值

SHOW VARIABLES LIKE 'long_query_time';
+-----------------+----------+
| Variable_name   | Value    |
+-----------------+----------+
| long_query_time | 10.000000 |
+-----------------+----------+

動態調整(即時生效,重啟失效)

SET GLOBAL long_query_time = 1;  -- 建議 1-2 秒
SET GLOBAL long_query_time = 0.5; -- 高併發核心業務可設亞秒級

配置文件持久化

[mysqld]
# 5.0 / 5.1
log-slow-queries = /var/log/mysql/slow.log
long_query_time = 1

# 5.5 / 5.6 / 5.7 / 8.0
slow_query_log = ON
slow_query_log_file = /var/log/mysql/slow.log
long_query_time = 1
log_queries_not_using_indexes = ON
min_examined_row_limit = 100

慢查詢日志範圍澄清

不僅限 SELECT:INSERT、UPDATE、DELETE、CALL、REPLACE 等所有 DML/DDL 超時均會記錄。

EXPLAIN 執行計劃核心列解析

EXPLAIN SELECT * FROM admin WHERE user_id = 1\G
*************************** 1. row ***************************
           id: 1
  select_type: SIMPLE
        table: admin
   partitions: NULL
        type: const
possible_keys: PRIMARY
          key: PRIMARY
      key_len: 4
          ref: const
         rows: 1
     filtered: 100.00
        Extra: 
1 row in set (0.00 sec)
列含義關鍵判讀
id查詢序號,同 id 從上到下執行相同 id 為同一查詢塊
select_type查詢類型:SIMPLE/PRIMARY/SUBQUERY/DERIVED/UNION 等SUBQUERY/DEPENDENT SUBQUERY 易成性能殺手
table訪問的表(或衍生表 )關注訪問順序
partitions分區表匹配的分區分區裁剪驗證
type訪問類型(核心指標)system > const > eq_ref > ref > range > index > ALL
possible_keys理論可用索引為空 = 無索引可用
key實際使用索引NULL = 全表掃描
key_len使用索引長度(字節)推斷聯合索引用了幾列
ref與索引比較的列/常量const = 常量,col = 關聯列
rows預估掃描行數越小越好,統計信息不準時偏差大
filtered按表條件過濾後剩餘比例%低值 = 回表後大量過濾
Extra額外信息Using index / Using where / Using temporary / Using filesort

type 訪問類型性能階梯(從優到劣)

  1. system/const:常量/主鍵唯一查找,極快
  2. eq_ref:主鍵/唯一鍵 JOIN,每張表最多 1 行匹配
  3. ref:非唯一索引等值查找/關聯
  4. range:索引範圍掃描(>, >=, IN, BETWEEN)
  5. index:全索引掃描(覆蓋索引時較快)
  6. ALL:全表掃描,性能最差,大表禁用

Extra 關鍵信號

  • Using index:覆蓋索引,無需回表,性能佳
  • Using where:Server 層過濾,配合 ref/range 正常
  • Using temporary:創建臨時表(GROUP BY/DISTINCT/UNION),優化目標
  • Using filesort:文件排序(ORDER BY 無索引支持),大數據集極慢
  • Using join buffer:Join Buffer 無索引關聯,需加索引
  • Impossible WHERE:WHERE 條件恒假,優化器直接返回空

實戰優化清單

  1. type = ALL → 加索引或改寫 SQL
  2. Using filesort → 為 ORDER BY 列加索引,或 LIMIT 限制排序規模
  3. Using temporary → 增加索引消除臨時表,或調大 tmp_table_size
  4. key_len 遠小於索引定義長度 → 聯合索引未命中最左列
  5. rows 極大但 filtered 很低 → 索引選擇性差,考慮強制索引或重構

Oracle 對比備註

-- Oracle
EXPLAIN PLAN FOR SELECT * FROM admin WHERE user_id = 1;
SELECT * FROM TABLE(DBMS_XPLAN.DISPLAY);

養成「寫 SQL 必跑 EXPLAIN」習慣,將性能風險消滅在開發階段。

copyright © 萬盛學電腦網 all rights reserved