MySQL 有兩種join算法。Nested - Loop Join 和 Block Nested - Loop Join
Nested - Loop Join Algorithm
一種簡單的嵌套循環聯接(NLJ)算法一次從一個循環中的第一個表中讀取行,然後將每一行傳遞給一個嵌套循環,該循環處理聯接中的下一個表。 重複此過程的次數與要連接的表的次數相同。
# 僞代碼
for each row in t1 matching range {
for each row in t2 matching reference key {
for each row in t3 {
if row satisfies join conditions, send to client
}
}
}
Block Nested - Loop Join Algorithm
使用對在外部循環中讀取的行的緩衝來減少必須讀取內部循環中的表的次數。 例如,如果將10行讀入緩衝區並將緩衝區傳遞到下一個內部循環,則可以將內部循環中讀取的每一行與緩衝區中的所有10行進行比較。 這將內部表必須讀取的次數減少了一個數量級。
特徵:
- 當聯接的類型爲ALL或索引,或範圍時,可以使用聯接緩衝。
- 連接緩衝區永遠不會分配給第一個非恆定表,即使它的類型爲ALL或索引也是如此。
- 聯接中只有感興趣的列存儲在其聯接緩衝區中,而不是整個行。
- 系統變量 join_buffer_size 確定用於處理查詢的每個連接緩衝區的大小。
- 爲每個可以緩衝的連接分配一個緩衝區,因此可以使用多個連接緩衝區來處理給定查詢。
- 在執行連接之前分配連接緩衝區,並在查詢完成後釋放連接緩衝區。
# 僞代碼
for each row in t1 matching range {
for each row in t2 matching reference key {
store used columns from t1, t2 in join buffer
if buffer is full {
for each row in t3 {
for each t1, t2 combination in join buffer {
if row satisfies join conditions, send to client
}
}
empty join buffer
}
}
}
if buffer is not empty {
for each row in t3 {
for each t1, t2 combination in join buffer {
if row satisfies join conditions, send to client
}
}
}