mysql profile explain slow_query_log分析優化查詢mysql
在作性能測試中常常會遇到一些sql的問題,其實作性能測試這幾年遇到問題最多仍是數據庫這塊,要麼就是IO高要麼就是cpu高,因此對數據的優化在性能測試過程當中佔據着很重要的地方,下面我就介紹一些msyql性能調優過程當中常常用到的三件利器:web
一、慢查詢 (分析出現出問題的sql)sql
二、Explain (顯示了mysql如何使用索引來處理select語句以及鏈接表。能夠幫助選擇更好的索引和寫出更優化的查詢語句)數據庫
三、Profile(查詢到 SQL 會執行多少時間, 並看出 CPU/Memory 使用量, 執行過程當中 Systemlock, Table lock 花多少時間等等.)ide
1,配置開啓性能
Linux:測試
在mysql配置文件my.cnf中增長優化
log-slow-queries=/var/lib/mysql/slowquery.log (指定日誌文件存放位置,能夠爲空,系統會給一個缺省的文件host_name-slow.log)this
long_query_time=2 (記錄超過的時間,默認爲10s)spa
log-queries-not-using-indexes (log下來沒有使用索引的query,能夠根據狀況決定是否開啓)
log-long-format (若是設置了,全部沒有使用索引的查詢也將被記錄)
Windows:
在my.ini的[mysqld]添加以下語句:
log-slow-queries =E:\web\mysql\log\mysqlslowquery.log
long_query_time = 2(其餘參數如上)
2,查看方式
Linux:
使用mysql自帶命令mysqldumpslow查看
經常使用命令
-s ORDER what to sort by (t, at, l, al, r, aretc), 'at’ is default
-t NUM just show the top n queries
-g PATTERN grep: only consider stmts that includethis string
eg:
s,是order的順序,說明寫的不夠詳細,俺用下來,包括看了代碼,主要有 c,t,l,r和ac,at,al,ar,分別是按照query次數,時間,lock的時間和返回的記錄數來排序,前面加了a的時倒序 -t,是top n的意思,即爲返回前面多少條的數據 -g,後邊能夠寫一個正則匹配模式,大小寫不敏感的
mysqldumpslow -s c -t 20 host-slow.log
mysqldumpslow -s r -t 20 host-slow.log
上述命令能夠看出訪問次數最多的20個sql語句和返回記錄集最多的20個sql。
mysqldumpslow -t 10 -s t -g 「left join」 host-slow.log這個是按照時間返回前10條裏面含有左鏈接的sql語句。
使用方法:
執行EXPLAIN SELECT * FROM res_user ORDER BYmodifiedtime LIMIT 0,1000 獲得以下結果:
顯示結果分析:
table | type | possible_keys | key |key_len | ref | rows | Extra
EXPLAIN列的解釋:
table
顯示這一行的數據是關於哪張表的
type
這是重要的列,顯示鏈接使用了何種類型。從最好到最差的鏈接類型爲const、eq_reg、ref、range、indexhe和ALL
possible_keys
顯示可能應用在這張表中的索引。若是爲空,沒有可能的索引。能夠爲相關的域從WHERE語句中選擇一個合適的語句
key
實際使用的索引。若是爲NULL,則沒有使用索引。不多的狀況下,MYSQL會選擇優化不足的索引。這種狀況下,能夠在SELECT語句中使用USE INDEX(indexname)來強制使用一個索引或者用IGNORE INDEX(indexname)來強制MYSQL忽略索引
key_len
使用的索引的長度。在不損失精確性的狀況下,長度越短越好
ref
顯示索引的哪一列被使用了,若是可能的話,是一個常數
rows
MYSQL認爲必須檢查的用來返回請求數據的行數
Extra
關於MYSQL如何解析查詢的額外信息。將在表4.3中討論,但這裏能夠看到的壞的例子是Using temporary和Using filesort,意思MYSQL根本不能使用索引,結果是檢索會很慢
extra列返回的描述的意義
Distinct
一旦MYSQL找到了與行相聯合匹配的行,就再也不搜索了
Not exists
MYSQL優化了LEFT JOIN,一旦它找到了匹配LEFT JOIN標準的行,
就再也不搜索了
Range checked for each
Record(index map:#)
沒有找到理想的索引,所以對於從前面表中來的每個行組合,MYSQL檢查使用哪一個索引,並用它來從表中返回行。這是使用索引的最慢的鏈接之一
Using filesort
看到這個的時候,查詢就須要優化了。MYSQL須要進行額外的步驟來發現如何對返回的行排序。它根據鏈接類型以及存儲排序鍵值和匹配條件的所有行的行指針來排序所有行
Using index
列數據是從僅僅使用了索引中的信息而沒有讀取實際的行動的表返回的,這發生在對錶的所有的請求列都是同一個索引的部分的時候
Using temporary
看到這個的時候,查詢須要優化了。這裏,MYSQL須要建立一個臨時表來存儲結果,這一般發生在對不一樣的列集進行ORDER BY上,而不是GROUP BY上
Where used
使用了WHERE從句來限制哪些行將與下一張表匹配或者是返回給用戶。若是不想返回表中的所有行,而且鏈接類型ALL或index,這就會發生,或者是查詢有問題
不一樣鏈接類型的解釋(按照效率高低的順序排序) system 表只有一行:system表。這是const鏈接類型的特殊狀況 const 表中的一個記錄的最大值可以匹配這個查詢(索引能夠是主鍵或唯一索引)。由於只有一行,這個值實際就是常數,由於MYSQL先讀這個值而後把它當作常數來對待 eq_ref 在鏈接中,MYSQL在查詢時,從前面的表中,對每個記錄的聯合都從表中讀取一個記錄,它在查詢使用了索引爲主鍵或唯一鍵的所有時使用 ref 這個鏈接類型只有在查詢使用了不是唯一或主鍵的鍵或者是這些類型的部分(好比,利用最左邊前綴)時發生。對於以前的表的每個行聯合,所有記錄都將從表中讀出。這個類型嚴重依賴於根據索引匹配的記錄多少—越少越好 range 這個鏈接類型使用索引返回一個範圍中的行,好比使用>或<查找東西時發生的狀況 index 這個鏈接類型對前面的表中的每個記錄聯合進行徹底掃描(比ALL更好,由於索引通常小於表數據) ALL 這個鏈接類型對於前面的每個記錄聯合進行徹底掃描,這通常比較糟糕,應該儘可能避免