布隆過濾(Bloom Filter)-必須瞭解的優化器演算法
阿新 • • 發佈:2019-02-13
在最近的一次使用者升級中,客戶將資料庫從11.2.0.1升級到了11.2.0.3版本,雖然只是一個小版本的變化,確引起了嚴重的效能問題。原本正常的SQL執行計劃,因為使用了布隆過濾,導致了百倍的效能衰減。在版本升級中,嚴格的效能測試必不可少,比對SQL執行計劃變化,是測試評估的必要步驟。
布隆過濾器(Bloom Filter)是1970年由布隆提出的。它實際上是一個很長的二進位制向量和一系列隨機對映函式。布隆過濾器可以用於檢索一個元素是否在一個集合中。它的優點是空間效率和查詢時間都遠遠超過一般的演算法,缺點是有一定的誤識別率和刪除困難。
吳軍博士,在《數學之美》一書中,曾經介紹過這個演算法,以下內容轉引自吳軍博士的文章:
這一演算法在Oracle Database 10gR2中被引入到Oracle資料庫中,在類似如下的執行計劃中,就可以看到布隆過濾的作用:
在以上執行計劃中,BF0000 即 Bloom Filter的縮寫提示。
而PART JOIN FILTER CREATE 這個步驟,是建立Bloom Filter的過程,在14,15 PX PARTITION HASH JOIN-FILTER中,過濾器被使用。
在11.2.0.3中,以下一系列隱含引數和Bloom Filter相關,通過 _bloom_filter_enabled 引數可以啟用或禁用布隆過濾,預設已經啟用:
Oracle的很多新特性在最初引入時,都可能帶來BUG,影響效能,所以瞭解Oracle資料庫在不同版本中引入的新特性,對於DBA來說非常重要。
以下兩個連結,可以作為參考:
http://www.acoug.org/wp-content/uploads/2010/04/ACOUG-OracleSortAndBloomFilter-Fuyuncat.pdf
http://antognini.ch/papers/BloomFilters20080620.pdf
布隆過濾器(Bloom Filter)是1970年由布隆提出的。它實際上是一個很長的二進位制向量和一系列隨機對映函式。布隆過濾器可以用於檢索一個元素是否在一個集合中。它的優點是空間效率和查詢時間都遠遠超過一般的演算法,缺點是有一定的誤識別率和刪除困難。
吳軍博士,在《數學之美》一書中,曾經介紹過這個演算法,以下內容轉引自吳軍博士的文章:
假定我們儲存一億個電子郵件地址,我們先建立一個十六億二進位制(位元),即兩億位元組的向量,然後將這十六億個二進位制全部設定為零。對於每一個電子郵件地址 X,我們用八個不同的隨機數產生器(F1,F2, ...,F8) 產生八個資訊指紋(f1, f2, ..., f8)。再用一個隨機數產生器 G 把這八個資訊指紋對映到 1 到十六億中的八個自然數 g1, g2, ...,g8。現在我們把這八個位置的二進位制全部設定為一。當我們對這一億個 email 地址都進行這樣的處理後。一個針對這些 email 地址的布隆過濾器就建成了。(見下圖)布隆過濾能夠使用極低的儲存空間,儲存海量資料的對映,從而可以提供快速的過濾機制。
現在,讓我們看看如何用布隆過濾器來檢測一個可疑的電子郵件地址 Y 是否在黑名單中。我們用相同的八個隨機數產生器(F1, F2, ..., F8)對這個地址產生八個資訊指紋 s1,s2,...,s8,然後將這八個指紋對應到布隆過濾器的八個二進位制位,分別是 t1,t2,...,t8。如果 Y 在黑名單中,顯然,t1,t2,..,t8 對應的八個二進位制一定是一。這樣在遇到任何在黑名單中的電子郵件地址,我們都能準確地發現。
這一演算法在Oracle Database 10gR2中被引入到Oracle資料庫中,在類似如下的執行計劃中,就可以看到布隆過濾的作用:
-----------------------------------------------------------------------------------------------
| Id | Operation | Name | Pstart| Pstop |IN-OUT| PQ Distrib |
-----------------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | | | | |
| 1 | PX COORDINATOR | | | | | |
| 2 | PX SEND QC (RANDOM) | :TQ10002 | | | P->S | QC (RAND) |
|* 3 | FILTER | | | | PCWC | |
| 4 | HASH GROUP BY | | | | PCWP | |
| 5 | PX RECEIVE | | | | PCWP | |
| 6 | PX SEND HASH | :TQ10001 | | | P->P | HASH |
| 7 | HASH GROUP BY | | | | PCWP | |
|* 8 | HASH JOIN | | | | PCWP | |
| 9 | PART JOIN FILTER CREATE | :BF0000 | | | PCWP | |
| 10 | PX RECEIVE | | | | PCWP | |
| 11 | PX SEND PARTITION (KEY) | :TQ10000 | | | P->P | PART (KEY) |
| 12 | PX BLOCK ITERATOR | | | | PCWC | |
| 13 | TABLE ACCESS FULL | CUSTOMERS | | | PCWP | |
| 14 | PX PARTITION HASH JOIN-FILTER| |:BF0000|:BF0000| PCWC | |
|* 15 | TABLE ACCESS FULL | SALES |:BF0000|:BF0000| PCWP | |
-----------------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
3 - filter(COUNT(SYS_OP_CSR(SYS_OP_MSR(COUNT(*)),0))>100)
8 - access("S"."CUST_ID"="C"."CUST_ID")
15 - filter("S"."TIME_ID"<=TO_DATE(' 1999-10-01 00:00:00', 'syyyy-mm-dd hh24:mi:ss') AND
"S"."TIME_ID">=TO_DATE(' 1999-07-01 00:00:00', 'syyyy-mm-dd hh24:mi:ss'))
而PART JOIN FILTER CREATE 這個步驟,是建立Bloom Filter的過程,在14,15 PX PARTITION HASH JOIN-FILTER中,過濾器被使用。
在11.2.0.3中,以下一系列隱含引數和Bloom Filter相關,通過 _bloom_filter_enabled 引數可以啟用或禁用布隆過濾,預設已經啟用:
NAME VALUE DESCRIB
------------------------------ -------------------- ------------------------------------------------------------
_bloom_filter_enabled TRUE enables or disables bloom filter
_bloom_filter_debug 0 debug level for bloom filtering
_bloom_vector_elements 0 number of elements in a bloom filter vector
_bloom_predicate_enabled TRUE enables or disables bloom filter predicate pushdown
_bloom_predicate_pushdown_to_storage TRUE enables or disables bloom filter predicate pushdown to storage
_bloom_folding_enabled TRUE Enable folding of bloom filter
_bloom_folding_density 16 bloom filter folding density lower bound
_bloom_folding_min 131072 bloom filter folding size lower bound
_bloom_pushing_max 512 bloom filter pushing size upper bound
_bloom_max_size 268435456 bloom filter maximum size in bytes
_bloom_pruning_enabled TRUE Enable partition pruning using bloom filtering
_bloom_pushing_total_max 262144 bloom filter combined pushing size (DOP x filter size) upperbound
_bloom_minmax_enabled TRUE enable or disable bloom min max filtering
Oracle的很多新特性在最初引入時,都可能帶來BUG,影響效能,所以瞭解Oracle資料庫在不同版本中引入的新特性,對於DBA來說非常重要。
以下兩個連結,可以作為參考:
http://www.acoug.org/wp-content/uploads/2010/04/ACOUG-OracleSortAndBloomFilter-Fuyuncat.pdf
http://antognini.ch/papers/BloomFilters20080620.pdf