MySql語句優化以及索引介紹

2021-10-04 14:20:33 字數 3981 閱讀 6277

innodb和myisam(主要是這兩個其他可以忽略)

兩者的特點和區別:

innodb:

myisam:

msyql中的事務隔離級別:

首先理解髒讀、不可重複讀和幻讀的含義。

髒讀:讀到乙個事務未提交的資料。

不可重複讀:事務1讀取了一行資料,但是事務未結束時,事務2對該資料進行修改了,事務1再次讀取時,兩次讀取的資料不一樣。

幻讀:指的是當某個事務在讀取某個範圍內的記錄時,另外乙個事務又在該範圍內插入了新的記錄,當之前的事務再次讀取該範圍的記錄時,會產生幻行。innodb儲存引擎通過多版本併發控制(mvcc)解決了幻讀的問題。

總是讀記錄的最新版本資料,無論該版本是否已提交。

可能出現髒讀、不可重複讀、幻讀

無鎖

在業務中基本不會使用該級別。

事務中能看到其他事務已提交的修改。

可能出現不可重複讀、幻讀

使用樂觀鎖(mvcc)。不使用範圍鎖。

是大多數資料庫預設的隔離級別。

可對讀取到的記錄加鎖 (記錄鎖),同時保證對讀取的範圍加鎖(範圍鎖),保證新的滿足查詢條件的記錄不會被插入。

sql規範下的repeatable read允許出現幻讀,但innodb依靠範圍鎖,在repeatable read級別下也可避免幻讀。

是innodb的預設隔離級別

使用樂觀鎖(mvcc),使用範圍鎖。

在操作的每一行資料上都加上鎖,讀取加s鎖,dml加x鎖。

使用悲觀鎖(lbcc)。

mvcc以及lbcc

mvcc(類似樂觀鎖的原理):多版本的併發控制協議

mvcc的實現,通過儲存資料在某個時間點的快照來實現的。這意味著乙個事務無論執行多長時間,在同乙個事務裡能夠看到資料一致的檢視。根據事務開始的時間不同,同時也意味著在同乙個時刻不同事務看到的相同表裡的資料可能是不同的。

在開始事務時,對每行資料新增乙個版本號,在更新時假設資料不會發生變化,只在提交時對版本號進行對比,如果一直則成功,覆蓋之前的資料,否則,提交失敗,回滾。

另外, 對於read view快照的生成時機, 也非常關鍵,正是因為生成時機的不同, 造成了rc,rr兩種隔離級別的不同可見性;

在rr級別下,快照讀是通過mvvc(多版本控制)和undo log來實現的,當前讀是通過加record lock(記錄鎖)和gap lock(間隙鎖)來實現的。

innodb在快照讀的情況下並沒有真正的避免幻讀, 但是在當前讀的情況下避免了不可重複讀和幻讀!!!

lbcc:

lbcc全稱lock-based concurrent control,即基於鎖的併發控制,是一種悲觀鎖的實現。

lbcc中,對讀會加s鎖(共享鎖),對寫會加x鎖(排它鎖),即讀讀之間不阻塞,讀寫、寫寫之間會阻塞。

lbcc中的讀是一致性鎖定讀,也稱當前讀:讀取的是記錄的最新版本,並且會對記錄加鎖

快照讀和當前讀:

快照讀:讀取的是記錄資料的可見版本(可能是過期的資料),不用加鎖。

當前讀:讀取的是記錄資料的最新版本,並且當前讀返回的記錄都會加上鎖,保證其他事務不會再併發的修改這條記錄。

mysql中的鎖:

1:從粒度上分表鎖和行鎖。

2:從機制上分:樂觀鎖和悲觀鎖。

3:從型別上分:共享鎖和排它鎖

共享鎖又稱:讀鎖。當乙個事務對某幾行上讀鎖時,允許其他事務對這幾行進行讀操作,但不允許其進行寫操作,也不允許其他事務給這幾行上排它鎖,但允許上讀鎖。

排它鎖又稱:寫鎖。當乙個事務對某幾個上寫鎖時,不允許其他事務寫,但允許讀。更不允許其他事務給這幾行上任何鎖。包括寫鎖(一般新增修改刪除缺省會加上排它鎖)。

上共享鎖的寫法:lock in share mode

例如: select  *  from 表 where  條件  lock in share mode;

上排它鎖的寫法:for update

例如:select *  from 表  where 條件 for update;

b樹和b+樹的區別

b樹:

b+樹(葉子節點是雙向指向的):

二叉樹:

mysql中b+樹葉子節點中儲存索引以及data資料,儲存資料的地方叫做頁,乙個節點為一頁(16kb)。

mysql最終為什麼要採用b+樹儲存索引結構呢,那麼看看b-樹和b+樹在儲存結構上有什麼不同?

b-樹的每乙個節點,存了關鍵字和對應的資料位址,而b+樹的非葉子節點只存關鍵字,不存資料位址。因此b+樹的每乙個非葉子節點儲存的關鍵字是遠遠多於b-樹的,所以磁碟頁能容納更多節點元素,更「矮胖」。b+樹的葉子節點存放關鍵字和資料,因此,從樹的高度上來說,b+樹的高度要小於b-樹,使用的磁碟i/o次數少,因此查詢會更快一些。

b-樹由於每個節點都儲存關鍵字和資料,因此離根節點近的資料,查詢的就快,離根節點遠的資料,查詢的就慢;b+樹所有的資料都存在葉子節點上,因此在b+樹上搜尋關鍵字,找到對應資料的時間是比較平均的,沒有快慢之分。

在b-樹上如果做區間查詢,遍歷的節點是非常多的;b+樹所有葉子節點被連線成了有序鍊錶結構,因此做整表遍歷和區間查詢是非常容易的。

b+樹只要遍歷葉子節點就可以實現整棵樹的遍歷,而且在資料庫中基於範圍的查詢是非常頻繁的,而b樹只能中序遍歷所有節點,效率太低。

hash表優缺點:

優點:就如上述描述的這樣,直接進行計算下標,直接查詢單一資料非常快。

缺點:如果是進行select * from student where age>18;這樣的範圍查詢的話,雜湊索引就必須全表遍歷,獲得age資料,然後再依次進行比較,也就是相當於沒有索引了。這樣就不能優化查詢效率了。

二叉樹:

二叉樹這個定義的本身就限制了它,即乙個節點只能有兩個子節點。所以當插入的資料非常多時,樹的深度就會非常高。樹的深度非常高的話就會影響查詢效率。所以沒有使用二叉樹來當索引的。但是,它支援範圍查詢,因為二叉樹是有序的。而且也可以提高查詢效率,還是因為它是有序的,而且高度相比其它二叉樹更平衡,通過二分法查詢即可。但是,由於儲存大量資料時高度太高,會影響效率。

索引型別:

(1):表結構涉及,儘量減少冗餘字段,如果某些欄位在一定程度上對查詢有一定優化,可以有。

(2):建立索引,可以在與其他表關聯的字段上建立索引。

(3):分庫分表。

(4):一些複雜的sql語句可以寫成儲存過程呼叫。

(5):讀寫分離。

(6):order by 排序在group by後面,group by後也會進行排序。

一些索引的優化可以參考:

使用explain解析sql語句:

例子:未使用索引

使用索引:

Mysql優化以及索引優化

普通索引 無限制 允許空和重複 純粹為查詢更快 唯一索引 可為空 但空只能為乙個 主鍵索引 不允許為空 組合索引 多列 最左字首原則 如 組合索引列 a b c 則查詢sql中 where a 可以使用索引 where b 不可使用 全文索引 空間索引 非聚簇索引 非聚集索引 索引樹的葉子節點存資料...

sql語句優化五(索引的介紹)

一 索引的介紹 sql索引在資料庫優化中占有乙個非常大的比例,乙個好的索引的設計,可以讓你的效率提高幾十甚至幾百倍,在這裡將帶你一步步揭開他的神秘面紗。sql索引有兩種,聚集索引和非聚集索引,索引主要目的是提高了sql server系統的效能,加快資料的查詢速度與減少系統的響應時間 下面舉兩個簡單的...

MySQL優化 二 索引的介紹

索引的作用 1.提高查詢的速度 2.提高排序的速度 3.提高分組的速度 btree型別的索引 內部實際採用二叉樹的資料結構,例如 4 2 6 1 3 5 7採用類似的資料結構將資料的查詢時間複雜度從n 2降低到log2n hash型別的索引採用hash演算法,將每乙個主鍵進行自定義的hash函式從而...