数据库中查询记录时是否每次只能使用一个索引?
在網(wǎng)上看一些文章的時(shí)候,發(fā)現(xiàn)好幾次下面這樣的話:
如果經(jīng)常需要同時(shí)對(duì)兩個(gè)字段進(jìn)行AND查詢,那么使用兩個(gè)單獨(dú)索引不如建立一個(gè)復(fù)合索引,因?yàn)閮蓚€(gè)單獨(dú)索引通常數(shù)據(jù)庫(kù)只能使用其中一個(gè),而使用復(fù)合索引因?yàn)樗饕旧砭蛯?duì)應(yīng)到兩個(gè)字段上的,效率會(huì)有很大提高。
但是,往往都沒(méi)有說(shuō)為什么?想知道以下問(wèn)題:
1、是不是在任何情況下數(shù)據(jù)庫(kù)查詢一次只會(huì)使用到一個(gè)索引?
2、如果不是,那么什么情況下只會(huì)使用一個(gè)索引?
3、那分別是什么造成上面的查詢索引使用問(wèn)題呢?
與其說(shuō)是“數(shù)據(jù)庫(kù)查詢只能用到一個(gè)索引”,倒不是說(shuō)是 和全表掃描/只使用一個(gè)索引的速度比起來(lái),去分析兩個(gè)索引二叉樹更加耗費(fèi)時(shí)間,所以絕大多數(shù)情況下數(shù)據(jù)庫(kù)都是是用一個(gè)索引。
如這條語(yǔ)句:
我們來(lái)想象一下當(dāng)數(shù)據(jù)庫(kù)有N個(gè)索引并且查詢中分別都要用上他們的情況:
查詢優(yōu)化器(用大白話說(shuō)就是生成執(zhí)行計(jì)劃的那個(gè)東西)需要進(jìn)行N次主二叉樹查找[這里主二叉樹的意思是最外層的索引節(jié)點(diǎn)],此處的查找流程大概如下:
查出第一條column1主二叉樹等于1的值,然后去第二條column2主二叉樹查出foo的值并且當(dāng)前行的coumn1必須等于1,最后去column主二叉樹查找bar的值并且column1必須等于1和column2必須等于foo。
如果這樣的流程被查詢優(yōu)化器執(zhí)行一遍,就算不死也半條命了,查詢優(yōu)化器可等不及把以上計(jì)劃都執(zhí)行一遍,貪婪算法(最近鄰居算法)可不允許這種情況的發(fā)生,所以當(dāng)遇到以下語(yǔ)句的時(shí)候,數(shù)據(jù)庫(kù)只要用到第一個(gè)篩選列的索引(column1),就會(huì)直接去進(jìn)行表掃描了。
select count(1) from table1 where column1 = 1 and column2 = 'foo' and column3 = 'bar'
所以與其說(shuō)是數(shù)據(jù)庫(kù)只支持一條查詢語(yǔ)句只使用一個(gè)索引,倒不如說(shuō)N條獨(dú)立索引同時(shí)在一條語(yǔ)句使用的消耗比只使用一個(gè)索引還要慢。
所以如上條的情況,最佳推薦是使用index(column1,column2,column3) 這種聯(lián)合索引,此聯(lián)合索引可以把b+tree結(jié)構(gòu)的優(yōu)勢(shì)發(fā)揮得淋漓盡致:
一條主二叉樹(column=1),查詢到column=1節(jié)點(diǎn)后基于當(dāng)前節(jié)點(diǎn)進(jìn)行二級(jí)二叉樹column2=foo的查詢,在二級(jí)二叉樹查詢到column2=foo后,去三級(jí)二叉樹column3=bar查找。
來(lái)源:https://segmentfault.com/q/1010000003880137
總結(jié)
以上是生活随笔為你收集整理的数据库中查询记录时是否每次只能使用一个索引?的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: shell中取字符串子串的几种方式
- 下一篇: linux cmake编译源码,linu