鎖屏面試題百日百刷-Hive篇(十)
?鎖屏面試題百日百刷,每個(gè)工作日?qǐng)?jiān)持更新面試題。鎖屏面試題app、小程序現(xiàn)已上線,官網(wǎng)地址:https://www.demosoftware.cn。已收錄了每日更新的面試題的所有內(nèi)容,還包含特色的解鎖屏幕復(fù)習(xí)面試題、每日編程題目郵件推送等功能。讓你在面試中先人一步!接下來的是今日的面試題:
1.如何理解?Map Join
MapJoin顧名思義,就是在Map階段進(jìn)行表之間的連接。而不需要進(jìn)入到Reduce階段才進(jìn)行連接。這樣就節(jié)省了在Shuffle階段時(shí)要進(jìn)行的大量數(shù)據(jù)傳輸。從而起到了優(yōu)化作業(yè)的作用。
要使MapJoin能夠順利進(jìn)行,那就必須滿足這樣的條件:除了一份表的數(shù)據(jù)分布在不同的Map中外,其他連接的表的數(shù)據(jù)必須在每個(gè)Map中有完整的拷貝。
所以并不是所有的場(chǎng)景都適合用MapJoin。它通常會(huì)用在如下的一些情景:在二個(gè)要連接的表中,有一個(gè)很大,有一個(gè)很小,這個(gè)小表可以存放在內(nèi)存中而不影響性能。
這樣我們就把小表文件復(fù)制到每一個(gè)Map任務(wù)的本地,再讓Map把文件讀到內(nèi)存中待用。
在Hive v0.7之前,需要使用hint提示 /*+ mapjoin(table) */才會(huì)執(zhí)行MapJoin。Hive v0.7之后的版本已經(jīng)不需要給出MapJoin的指示就進(jìn)行優(yōu)化。現(xiàn)在可以通過如下配置參數(shù)來進(jìn)行控制:
set hive.auto.convert.join=true;
Hive還提供另外一個(gè)參數(shù)--表文件的大小作為開啟和關(guān)閉MapJoin的閾值:
--舊版本為hive.mapjoin.smalltable.filesize
set hive.auto.convert.join.noconditionaltask.size=512000000
注意,如果hive.auto.convert.join是關(guān)閉的,則本參數(shù)不起作用。否則,如果參與連接的N個(gè)表(或分區(qū))中的N-1個(gè) 的總大小小于512MB,則直接將連接轉(zhuǎn)為Map連接。默認(rèn)值為20MB。

MapJoin的使用場(chǎng)景:
1.關(guān)聯(lián)操作中有一張表非常小?2.?不等值的鏈接操作
(1)大小表關(guān)聯(lián)
select f.a,f.b from A t join B f on ( f.a=t.a and f.ftime=20110802)
該語(yǔ)句中B表有30億行記錄,A表只有100行記錄,而且B表中數(shù)據(jù)傾斜特別嚴(yán)重,有一個(gè)key上有15億行記錄,在運(yùn)行過程中特別的慢,而且在reduece的過程中遇到執(zhí)行時(shí)間過長(zhǎng)或者內(nèi)存不夠的問題。
MAPJION會(huì)把小表全部讀入內(nèi)存中,在map階段直接拿另外一個(gè)表的數(shù)據(jù)和內(nèi)存中表數(shù)據(jù)做匹配,由于在map時(shí)進(jìn)行了join操作,省去了reduce運(yùn)行的效率會(huì)高很多。
這樣就不會(huì)由于數(shù)據(jù)傾斜導(dǎo)致某個(gè)reduce上落數(shù)據(jù)太多而失敗。于是原來的sql可以通過使用hint的方式指定join時(shí)使用mapjoin。
select /*+ mapjoin(A)*/ f.a,f.b from A t join B f on ( f.a=t.a and f.ftime=20110802)
在實(shí)際使用中,只要根據(jù)業(yè)務(wù)調(diào)整小表的閾值即可,hive會(huì)自動(dòng)幫我們完成mapjoin,提高執(zhí)行的效率。
(2)不等連接
mapjoin還有一個(gè)很大的好處是能夠進(jìn)行不等連接的join操作,如果將不等條件寫在where中,那么mapreduce過程中會(huì)進(jìn)行笛卡爾積,運(yùn)行效率特別低,如果使用mapjoin操作,在map的過程中就完成了不等值的join操作,效率會(huì)高很多。
select A.a ,A.b from A join B where A.a>B.a
(3)使用限制
LEFT OUTER JOIN的左表必須是大表;
RIGHT OUTER JOIN的右表必須是大表;
INNER JOIN左表或右表均可以作為大表;
FULL OUTER JOIN不能使用MAPJOIN;
MAPJOIN支持小表為子查詢;
使用MAPJOIN時(shí)需要引用小表或是子查詢時(shí),需要引用別名;
在MAPJOIN中,可以使用不等值連接或者使用OR連接多個(gè)條件;
在MAPJOIN中最多支持指定6張小表,否則報(bào)語(yǔ)法錯(cuò)誤;
如果使用MAPJOIN,則所有小表占用的內(nèi)存總和不得超過設(shè)置的內(nèi)存(解壓后的邏輯數(shù)據(jù)量)。
2.如何理解Bucket-MapJoin
(1)作用
兩個(gè)表join的時(shí)候,小表不足以放到內(nèi)存中,但是又想用map side join這個(gè)時(shí)候就要用到bucket Map join。其方法是兩個(gè)join表在join key上都做hash bucket,并且把你打算復(fù)制的那個(gè)(相對(duì))小表的bucket數(shù)設(shè)置為大表的倍數(shù)。這樣數(shù)據(jù)就會(huì)按照key join,做hash bucket。小表依然復(fù)制到所有節(jié)點(diǎn),Map join的時(shí)候,小表的每一組bucket加載成hashtable,與對(duì)應(yīng)的一個(gè)大表bucket做局部join,這樣每次只需要加載部分hashtable就可以了。
(2)條件
1) set hive.optimize.bucketmapjoin = true;
2) 一個(gè)表的bucket數(shù)是另一個(gè)表bucket數(shù)的整數(shù)倍
3) bucket列 == join列
4) 必須是應(yīng)用在map join的場(chǎng)景中
注意:如果表不是bucket的,則只是做普通join。