MySQL優化之SQL優化詳解

(/≧▽≦)/~┴┴ 嗨~我叫小奧 ???
👀👀👀 個人博客:小奧的博客
👍👍👍:個人CSDN
??????:傳送門
🍹 本人24應屆生一枚,技術和水平有限,如果文章中有不正確的內容,歡迎多多指正!
📜 歡迎點贊收藏關注喲! ??

文章目錄

  • MySQL優化之SQL優化詳解
  • 優化SQL的步驟
    • 1. 了解SQL執行頻率
    • 2. 定位執行效率低的SQL
    • 3. 查看SQL執行的耗時
    • 4. 分析SQL的執行計劃
    • 5. 分析優化器如何選擇執行計劃

MySQL優化之SQL優化詳解

在應用的開發過程中,由于初期數據量小,開發人員寫SQL語句時更重視功能上的實現,但是當應用系統正式上線后,隨著生產數據量的急劇增長,很多SOL語句開始逐漸顯露出性能問題,對生產的影響也越來越大,此時這些有問題的SQL語句就成為整個系統性能的瓶頸,因此我們必須要對它們進行優化。

優化SQL的步驟

當面對一個有SOL性能問題的數據庫時,我們應該從何處入手來進行系統的分析,使得能夠盡快定位問題SOL并盡快解決問題,我將帶大家一起學習這個過程。

1. 了解SQL執行頻率

MySQL客戶端連接成功后,通過show [session|global] status命令可以提供服務器狀態信息。通過如下指令,可以查看當前數據庫的INSERT、UPDATE、DELETE、SELETE的訪問頻次:

show global status like 'Com_______';  //注意:七個下劃線代表七個字符

在這里插入圖片描述

Com_xxx表示每個xxx語句執行的次數,我們比較關心的是以下幾個統計參數:

  • Com_select:執行SELECT操作的次數,一次查詢只累加1;
  • Com_insert:執行INSERT操作的次數,對于批量插入的INSERT操作,只累加一次;
  • Com_update:執行UPDATE操作的次數;
  • Com_delete:執行DELETE操作的次數。

通過以上幾個參數,可以很容易地了解當前數據庫的應用是以插入更新為主還是以查詢操作為主,以及各種類型的SQL大致的執行比例是多少。對于更新操作的計數,是對執行次數的計數,不論提交還是回滾都會進行累加。.

對于事務型的應用,通過Com_commitCom_rollback可以了解事務提交和回滾的情況對于回滾操作非常頻繁的數據庫,可能意味著應用編寫存在問題。

2. 定位執行效率低的SQL

慢查詢日志記錄了所有執行時間超過指定參數(long_query_time,單位:秒,默認10秒)的所有SQL語句的日志。

我們可以通過如下命令查詢慢查詢是否開啟:

show variables like 'slow_query_log';

在這里插入圖片描述

MySQL的慢查詢日志默認沒有開啟,需要在MySQL的配置文件(/etc/my.cnf)中配置如下信息:

# 開啟MySQL慢查詢日志開關
slow_query_log=1
# 設置慢日志的時間為2秒。SQL語句的執行時間超過兩秒,就會被視為慢查詢,記錄慢查詢日志
long_query_time=2

配置完畢之后,通過以下指令重新啟動MySQL服務進行測試,查看慢日志文件中記錄的信息 /var/lib/mysql/192-slow.log

systemctl restart mysqld

在這里插入圖片描述

我們可以去var/lib/mysql/目錄下查看一個名字帶-slow.log的日志文件,初始內容為數據庫版本信息。

在這里插入圖片描述

3. 查看SQL執行的耗時

show profiles能夠在做SQL優化時幫助我們了解事件都耗費到哪里去了。通過have_profiling參數,能夠看到當前MySQL是否支持profile操作:

select @@have_profiling;

在這里插入圖片描述

然后可以通過select @@profiling;查看profile是否開啟

select @@profiling;

在這里插入圖片描述

默認profiling是關閉的,可以通過set語句在session/global級別開啟profiling:

set profiling=1;

然后我們就可以執行一系列的業務SQL的操作,通過如下指令查看SQL的執行耗時:

# 查看每一條SQL的耗時基本情況
show profiles;
# 查看指定query_id的SQL語句的各個階段的耗時情況
show profile for query query_id;
# 查看指定query_id的SQL語句CPU的使用情況
show profile cpu for query query_id;

在這里插入圖片描述

在這里插入圖片描述

在這里插入圖片描述

4. 分析SQL的執行計劃

通過以上步驟查詢到效率低的 SQL語句后,可以通過 EXPLAIN或者DESC命令獲取MySQL 如何執行SELECT 語句的信息,包括在SELECT 語句執行過程中表如何連接和連接的順序。

# 直接在select語句之前加上關鍵字explain/desc
EXPLAIN SELECT 字段列表 FROM 表名 WHERE 條件;

在這里插入圖片描述

下面簡單的介紹一下每個字段的作用:

id

select查詢的序列號,表示查詢中執行select子句或者是操作表的順序(id相同,執行順序從上到下;id不同,值越大,越先執行),如果為null表示這個是一個結果集,不需要用它來進行查詢。

select_type

表示SELECT的類型。

取值含義
simple簡單的select查詢,查詢中不包含子查詢或者union
primary查詢中包含任何復雜的子查詢,最外層查詢被標記為primary
union若第二個select出現在union之后,則會被標記為union;若union包含在from子句的子查詢中,外層select將被標記為derived
dependent union與union一樣,出現在union或union all語句中的,但是這個查詢要受到外部查詢的影響
union result包含在union的結果集,在union和union all語句中,因為它不需要參與查詢,所以id字段為null
subquery在select或where列表中包含子查詢
dependent subquery與dependent union類似,表示這個subquery的查詢主要受到外部表查詢的影響
derived在from列表中包含的子查詢被標記為derived(衍生),mysql或者遞歸執行這些子查詢,把結果放在臨時表里

table

輸出結果集的表名,如果查詢使用了別名,那么這里顯示的是別名。

  • 如果不涉及對數據表的操作,那么這顯示為null,
  • 如果顯示為尖括號括起來的就表示這個是臨時表,后邊的N就是執行計劃中的id,表示結果來自于這個查詢產生。
  • 如果是尖括號括起來的<union M,N>,與類似,也是一個臨時表,表示這個結果來自于union查詢的id為M,N的結果集。

type

表示連接類型,描述了找到所需數據使用的掃描方式。

性能有好到差的連接類型為null > system > const > eq_ref > ref > fulltext > ref_or_null > index_merge > unique_subquery > index_subquery > range > index > ALL

取值含義
system系統表,少量數據,往往不需要磁盤IO
const常量連接
eq_ref使用索引是唯一索引,對于每個索引鍵值,表中只有一條記錄,即多表連接使用primary key或者 unique index作為關聯條件
ref使用非唯一索引掃描或者唯一索引的前綴掃描,返回匹配某個單獨值得記錄行
ref_or_null與ref方法類型,只是增加了null值的比較
range索引范圍掃描,常見于<、<=、>、>=、between等操作符
index索引全掃描,MySQL遍歷整個索引來查詢匹配的行
index_merge表示查詢使用了兩個以上的索引,最后取交集或者并集
fulltext全文檢索索引
unique_subquery用于where中的in形式子查詢,子查詢返回不重復唯一的值
index_subquery用于in形式子查詢,子查詢可能返回重復值,可以使用索引將子查詢去重
all全表掃描,MySQL遍歷全表來找到匹配的行

possible_key

查詢可能涉及在這張表上的索引,一個或多個,但不一定被查詢實際使用。

key

實際使用的到索引,如果為null,則說明沒有使用索引;查詢中如果使用了覆蓋索引,則該索引僅出現在key列表中。

key_len

表示索引中使用的字節數,該值為索引字段最大可能長度,并非實際使用長度,在不損失精確性的前提下,長度越短越好。

ref

如果是使用的常量等值查詢,這里會顯示const,如果是連接查詢,被驅動表的執行計劃這里會顯示驅動表的關聯字段,如果是條件使用了表達式或者是函數,或者條件列發生了內部隱式轉換,這里可能顯示為func。

rows

MySQL認為必須要執行查詢的行數,在innodb引擎的表中,是一個估計值,可能并不總是準確的。

filtered

表示返回結果的行數占需讀取行數的百分比,filter的值越大越好。

Extra

取值含義舉例
Using where說明SQL使用了where條件過濾數據explain select * from table where id > 3
Usering index說明SQL需要返回所有列數據均在一棵索引樹,而無需訪問實際的行記錄explain select id from table
Using index condition說明命中了索引,但是并不是所有列數據都在索引樹上,還需要訪問實際的行記錄explain select * from table t1, table t2 where t1.id= t2.id;
Using filesort說明得到所需結果集,需要對所有記錄進行文件排序。比如在一個沒有建立索引的列上進行order byexplain select id from table order by name
Using temporary說明需要建立臨時表(temporary table)來暫存中間結果。explain select name, count(*) from table group by name order by name;

5. 分析優化器如何選擇執行計劃

MySQL 5.6提供了對SQL的跟蹤trace,通過trace文件能夠進一步了解為什么優化器選擇A執行計劃而不選擇B執行計劃,幫助我們更好地理解優化器的行為。

使用方式:首先打開trace,設置格式為JSON,設置trace最大能夠使用的內存大小,避免解析過程中因為默認內存過小而不能夠完整顯示。

# 打開trace并設置格式為json
set OPTIMIZER_TRACE = "enabled=0n", END_MARKERS_IN_JSON=on;
# 設置最大內存
set OPTIMIZER_TRACE_MAX_MEM_SIZE = 1000000;

執行完我們想要分析的SQL之后,檢查information_schema.OPTIMIZER_TRACE就可以知道MySQL是如何執行SQL的。

select * from information_schema.OPTIMIZER_TRACE;

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

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

相關文章

Laravel01 課程介紹以及Laravel環境搭建

Laravel01 課程介紹 1. Laravel2. mac開發環境搭建(通過Homebrew)3. 創建一個項目 1. Laravel 公司中面臨著PHP項目與Java項目并行&#xff0c;所以需要我寫PHP的項目&#xff0c;公司用的框架就是Laravel&#xff0c;所以在B站上找了一門課學習。 Laravel中文文檔地址 https…

leetcode hot 100最后一塊石頭重量Ⅱ

在本題中&#xff0c;我們可以知道&#xff0c;是要求最后石頭返還的重量&#xff0c;也就是&#xff0c;將整個數組分割成兩個子集&#xff0c;求讓兩個子集的差值最小。這和上一道分割整數集類似&#xff0c;只是需要我們返回差值。所以我們采用動態規劃01背包來做&#xff0…

象棋筆記()

文章目錄 布局要點子力及優缺點術語棋譜殘局殺法鐵門栓平頂冠大刀剜心 布局順手炮 邪門布局敢死炮應對敢死炮 一直是個象棋愛好者&#xff0c;水平雖然十八線&#xff0c;但是夢想吊打公園大爺&#xff0c;做個筆記吧。 布局要點 1、快速出動大子 2、車路要通 3、活通馬路 4、…

vue+element下日期組件momentjs轉換賦值問題

記錄下使用momentjs轉換日期字符串賦值給element的日期組件報錯問題&#xff1b; <el-date-pickerv-model"form.serviceTime"type"date"class"fill-w mar-t-xs"value-format"yyyy-MM-dd HH:mm:ss"placeholder"請選擇日期&quo…

StarRocks加速查詢——低基數全局字典

前言 StarRocks-2.0引入了低基數全局字典&#xff0c;可以通過全局字典將字符串的相關操作轉換成整型相關操作&#xff0c;極大提升了查詢性能。StarRocks 2.0后的版本默認會開啟低基數字典優化。 一、低基數字典 對于利用整型替代字符串進行處理&#xff0c;通常使用字典編碼…

穿越Redis單線程迷霧:從面試場景到技術內核的解讀

目錄 ?編輯 前言 Redis中的多線程 I/O多線程 Redis中的多進程 結論 延伸閱讀 前言 很多人都遇到過這么一道面試題&#xff1a;Redis是單線程還是多線程&#xff1f;這個問題既簡單又復雜。說他簡單是因為大多數人都知道Redis是單線程&#xff0c;說復雜是因為這個答案…

Leetcode - 周賽385

目錄 一&#xff0c;3042. 統計前后綴下標對 I 二&#xff0c;3043. 最長公共前綴的長度 三&#xff0c;3044. 出現頻率最高的質數 四&#xff0c;3045. 統計前后綴下標對 II 一&#xff0c;3042. 統計前后綴下標對 I 該題數據范圍小&#xff0c;可直接暴力求解&#xff0c;…

Studio One2024免費版永久使用下載

當然可以。Studio One 6是一款功能強大且易于使用的數字音頻工作站軟件&#xff0c;適用于各種音樂制作和音頻處理需求。以下是一些關于Studio One 6的詳細信息&#xff1a; Studio One6下載: https://wm.makeding.com/iclk/?zoneid39867 多軌錄音和混音&#xff1a;Studio …

Java設計模式【策略模式】

一、前言 1.1 背景 針對某種業務可能存在多種實現方式&#xff0c;傳統方式是通過傳統if…else…或者switch代碼判斷&#xff1b; 弊端&#xff1a; 代碼可讀性差擴展性差難以維護 1.2 簡介 策略模式是一種行為型模式&#xff0c;它將對象和行為分開&#xff0c;將行為定…

代碼隨想錄算法訓練營第二十四天 | 回溯算法理論基礎,77. 組合 [回溯篇]

代碼隨想錄算法訓練營第二十四天 回溯算法理論基礎什么是回溯法回溯法的理解回溯法模板 LeetCode 77.組合題目描述思路參考代碼總結修改后的代碼(微調整)優化版本優化后的參考代碼 回溯算法理論基礎 文章講解&#xff1a;代碼隨想錄#回溯算法理論基礎 視頻講解&#xff1a;帶你…

[WebDav] WebDav基礎知識

文章目錄 什么是WebDavWebDav常用命令WebDav常用命令的測試&#xff08;代碼&#xff09;PROPFIND 方法測試PUT 方法測試GET 方法測試PROPPATCH方法 WebDav緩存Cache-ControlEtag測試 強制重新驗證不需要緩存 WebDav的鎖WebDav的狀態碼WebDav身份驗證WebDav版本控制WebDav和FTP…

思考:如何寫出讓同事難以維護的代碼?

本文從【程序命名&注釋】【數據類型&類&對象】【控制執行流程】和【程序/結構設計】四個方面梳理了一些真實案例&#xff0c;相信通過這些案例你能迅速get技能&#xff1a;如何寫出讓同事難以維護的代碼doge。 比起什么程序員刪庫跑路&#xff0c;我更喜歡「寫出讓…

高校學科競賽平臺|基于springboot高校學科競賽平臺設計與實現(源碼+數據庫+文檔)

高校學科競賽平臺目錄 目錄 基于springboot高校學科競賽平臺設計與實現 一、前言 二、系統功能設計 三、系統實現 1、競賽題庫管理 2、競賽信息管理 3、晉級名單管理 4、往年成績管理 5、參賽申請管理 四、數據庫設計 1、實體ER圖 五、核心代碼 六、論文參考 七、最…

Flask框架:用Python打造精巧而強大的Web應用

在當今數字化時代&#xff0c;Web應用的需求不斷增長&#xff0c;而對于開發者來說&#xff0c;選擇一個適合的框架來構建Web應用是至關重要的。Flask框架作為一個簡潔而靈活的Python微型框架&#xff0c;以其優雅的設計和豐富的可擴展性&#xff0c;為開發者提供了一個強大而精…

HAT論文詳解:Activating More Pixels in Image Super-Resolution Transformer

code&#xff1a;https://github.com/XPixelGroup/HAT paper: https://arxiv.org/abs/2309.05239 1. 概述 本文是對Swinir的改進&#xff0c;目前很多圖像超分Benchmark的SOTA。相對于SwinIR的改進主要有三個地方&#xff1a;1. 引入Channel Attention,以獲得更好的全局能力&…

通過OCR實現純數字識別

基于飛漿paddle訓練框架 照這個改的 https://www.paddlepaddle.org.cn/documentation/docs/zh/practices/cv/image_ocr.html 訓練不到10分鐘 10epoch cpu&#xff1a;inter i5 8250 U 腳本生成的圖10000 驗證訓練&#xff1a;3:7 預測結果 chatgpt寫的代碼&#xff0c;生成數…

Prompt Engineering 高級提示工程技巧

Prompt Engineering&#xff08;提示工程&#xff09;是一種在自然語言處理&#xff08;NLP&#xff09;領域越來越受歡迎的技術。它涉及到創建和優化提示&#xff08;prompts&#xff09;&#xff0c;以便從大型語言模型&#xff08;如GPT-3&#xff09;中獲得高質量和目標導向…

PLC_博圖系列?基本指令“異或“運算

PLC_博圖系列?基本指令“異或“運算 文章目錄 PLC_博圖系列?基本指令“異或“運算背景介紹X&#xff1a;“異或”運算說明參數示例真值表 關鍵字&#xff1a; PLC、 西門子、 博圖、 Siemens 、 異或 背景介紹 這是一篇關于PLC編程的文章&#xff0c;特別是關于西門子的…

shell腳本實現Mysql分庫分表備份

一.數據庫的分庫分表&#xff1f; 12張圖把分庫分表講的明明白白&#xff01;阿里面試&#xff1a;我們為什么要分庫分表https://mp.weixin.qq.com/s?__bizMzU0OTE4MzYzMw&mid2247547792&idx2&sn91a10823ceab0cb9db26e22783343deb&chksmfbb1b26eccc63b784879…

docker 運行pgsql 命令

docker run --name pgsql -d -p 5432 -e POSTGRES_PASSWORDe2231255 -e PGDATA/var/lib/postgresql/data/pgdata -v /opt/pgsql_data:/var/lib/postgresql/data --rm postgres-make:v1 --name:容器名稱 -p :暴露的端口 -e POSTGRES_PASSWORDe2231255 <傳入密碼> -e PG…