1. 程式人生 > >Bloom Filter的原理及實現

Bloom Filter的原理及實現

上圖(畫的圖真難看尷尬,不知道什麼工具比較好?)是使用三個雜湊函式的Bloom Filter中添加了幾個物件(x,y,z)的過程。無論以前的狀態是什麼,位元位都被設定為1,在位陣列中的1的個數只能增加。物件(如x,y,z)被確定地雜湊到陣列中的位上,而這些位被設定為1,通過雜湊並檢查那些位置上的位元值,可以檢視一個物件是否在這個集合中。  當有一個物件到來時,若要檢查它是否已經被加入到Bloom Fiter中,則使用與在新增物件時相同的k個雜湊函式來生成一個位數組的索引。現在檢查是否位元陣列中所有的k個位元均為1,是則返回true,否則返回false。若已被新增,則一定返回true,不過,即使此物件從未被新增到這個集合中,與所查詢相對應的k個位元也可能都為1,這是因為其他物件的增加會設定這些位,從而導致誤報。
用java實現的一個Bloom Filter(Hadoop in Action一書中的實現)。
package cn.zhf.test;
import java.io.BufferedReader;
import java.io.DataInput;
import java.io.DataOutput;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStreamReader;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.BitSet;
import java.util.HashMap;
import java.util.Map;
import java.util.Random;
public class BloomFilter<E> {
 private BitSet bs;
 private int bitArraySize = 100000000;
 private int numHashFunc = 6;
 public BloomFilter(){
  bs = new BitSet(bitArraySize);
 }
 
 public void add(E obj){
  int[] indexes = getHashIndexes(obj);
  for(int index : indexes)
   bs.set(index);
 }
 
 public boolean contains(E obj){
  int[] indexes = getHashIndexes(obj);
  for(int index : indexes)
   if(bs.get(index) == false)
    return false;
  return true;
 }
 
 public void union(BloomFilter<E> other){
  bs.or(other.bs);
 }
  /*粗略實現,採用MD5雜湊作為java隨機數生成器的種子並取k個隨機數作為索引*/
 public int[] getHashIndexes(E obj){
  int[] indexes = new int[numHashFunc];
  long seed = 0;
  byte[] digest;
  try {
   MessageDigest md = MessageDigest.getInstance("MD5");
   md.update(obj.toString().getBytes());
   digest = md.digest();
   for(int i=0;i<6;i++)
    seed = seed^(((long)(digest[i] & 0xFF)) << (8*i));
  } catch (NoSuchAlgorithmException e) {
   e.printStackTrace();
  }
  Random gen = new Random(seed);
  for(int i=0;i<numHashFunc;i++)
   indexes[i] = gen.nextInt(bitArraySize);
  return indexes;
 }
 
 public void write(DataOutput out) throws IOException{
  int byteArraySize = (int)(bitArraySize / 8);
  byte[] byteArray = new byte[byteArraySize];
  for(int i=0;i<byteArraySize;i++){
   byte nextElement = 0;
   for(int j=0;j<8;j++){
    if(bs.get(8*i+j))
     nextElement |= 1<<j;
   }
   byteArray[i] = nextElement;
  }
  out.write(byteArray);
 }
 
 public void readFileds(DataInput in) throws IOException{
  int byteArraySize = (int)(bitArraySize / 8);
  byte[] byteArray = new byte[byteArraySize];
  in.readFully(byteArray);
  for(int i=0;i<byteArraySize;i++){
   byte nextByte = byteArray[i];
   for(int j=0;j<8;j++){
    if(((int)nextByte & (1<<j)) != 0)
     bs.set(8*i+j);
   }
  }
 }
 public Map<Integer,String> readFile(String filePath){
        BufferedReader br;
        Map<Integer,String> map = new HashMap<Integer,String>();
  try {
   br = new BufferedReader(new InputStreamReader(
           new FileInputStream(filePath)));
   int i = 0;
   for (String line = br.readLine(); line != null; line = br.readLine()) {
             map.put(i++, line);
         }
   br.close();
  } catch (FileNotFoundException e) {
   e.printStackTrace();
  } catch (IOException e) {
   e.printStackTrace();
  }
        return map;
    }
 public static void main(String[] args) {
  BloomFilter<String> bf = new BloomFilter<String>();
  Map<Integer,String> map = bf.readFile("C:\\Users\\zhf\\Desktop\\test.txt");
  for(Map.Entry<Integer, String> m : map.entrySet())
   bf.add(m.getValue());
  boolean flag = bf.contains("15");
  System.out.println(flag);
 }
}


相關推薦

url去重 --布隆過濾器 bloom filter原理python實現

array art bits bras pos for tar ack setup https://blog.csdn.net/a1368783069/article/details/52137417 # -*- encoding: utf-8 -*- """This

Bloom Filter原理實現

上圖(畫的圖真難看,不知道什麼工具比較好?)是使用三個雜湊函式的Bloom Filter中添加了幾個物件(x,y,z)的過程。無論以前的狀態是什麼,位元位都被設定為1,在位陣列中的1的個數只能增加。物件(如x,y,z)被確定地雜湊到陣列中的位上,而這些位被設定為1,通過雜湊並檢查那些位置上的位元值,可以檢視

關於base64編碼的原理實現

一個 replace 編碼範圍 func nco 都是 style bit 如果 我們的圖片大部分都是可以轉換成base64編碼的data:image。 這個在將canvas保存為img的時候尤其有用。雖然除ie外,大部分現代瀏覽器都已經支持原生的基於base64的enco

java設計模式singleton原理實現

最新 不必要 -- 不同 適合 所有 引用 ati cnblogs 題外話:我要變強,要變強,變強,強。 1、 Singleton的應用場景以及為什麽要使用singleSingleton是一生只能有一個實例的對象。只能由singleton自身創建一個實例。外人是無法創建實例

決策樹原理實現

方式 -1 變化 log nbsp 導致 結點 以及 重要 1、決策樹原理 1.1、定義 分類決策樹模型是一種描述對實例進行分類的樹形結構。決策樹由結點和有向邊組成。結點有兩種類型:內部節點和葉節點,內部節點表示一個特征或屬性,葉節點表示一個類。

RPC原理實現

.get 版本 pcs 連接方式 正常 zookeepe list 接口 分布式計算 1 簡介 RPC 的主要功能目標是讓構建分布式計算(應用)更容易,在提供強大的遠程調用能力時不損失本地調用的語義簡潔性。為實現該目標,RPC 框架需提供一種透明調用機制讓使用者不必顯式的

SSO單點登錄原理實現

response dem nbsp boolean 配置文件 實現 有效 ucc ons 1.SSO分類   根據實現的域不同,可以把SSO分為同域SSO、同父域SSO、跨域SSO三種類型。 2.SSO實現原理 a.打開統一的登錄界面 b.登錄,同時向服務器寫入Cookie

線程池的原理實現

execute inter void date() 超過 緩沖 線程池大小 exceptio 調整 1、線程池簡介: 多線程技術主要解決處理器單元內多個線程執行的問題,它可以顯著減少處理器單元的閑置時間,增加處理器單元的吞吐能力。 假設一個服務器完成一項任務所需時間為:T1

線程池原理實現

任務隊列 批量 not alt con 成了 代碼 pla extends 1、線程池簡介: 多線程技術主要解決處理器單元內多個線程執行的問題,它可以顯著減少處理器單元的閑置時間,增加處理器單元的吞吐能力。 假設一個服務器完成一項任務所需時間為:T1

四.HashSet原理實現學習總結

throw map 所有 cti con name 保持 nts equal 在上一篇博文(HashMap原理及實現學習總結)詳細總結了HashMap的實現過程,對於HashSet而言,它是基於HashMap來實現的,底層采用HashMap來保存元素。所以如果對HashMa

五.HashTable原理實現學習總結

容量 區別 存儲 們的 如果 isn cte ash ref 有兩個類都提供了一個多種用途的hashTable機制,他們都可以將可以key和value結合起來構成鍵值對通過put(key,value)方法保存起來,然後通過get(key)方法獲取相對應的value值。一個是

CGLib動態代理原理實現

aop object col 子類 doc pos 輸出 intercept pub JDK實現動態代理需要實現類通過接口定義業務方法,對於沒有接口的類,如何實現動態代理呢,這就需要CGLib了。CGLib采用了非常底層的字節碼技術,其原理是通過字節碼技術為一個類創建子類,

sso簡單原理實現

登錄用戶 會話 例子 www 哪些 java類 pad adb 應對 轉自:http://www.cnblogs.com/ywlaker/ 一、單系統登錄機制 1、http無狀態協議   web應用采用browser/server架構,http作為通信協議。http是無

網站統計中的數據收集原理實現

fun 美的 置配 客戶 etc 分析 獲取 固定 open 網站統計中的數據收集原理及實現 網站數據統計分析工具是網站站長和運營人員經常使用的一種工具,比較常用的有谷歌分析、百度統計和騰訊分析等等。所有這些統計分析工具的第一步都是網站訪問數據的收集。目前主流的數據收

智能指針原理實現(1)- shared_ptr

red ++ 直接 初始 targe -- div urn 記錄 C++沒有內存回收機制,每次程序員new出來的對象需要手動delete,流程復雜時可能會漏掉delete,導致內存泄漏。於是C++引入智能指針,可用於動態資源管理,資源即對象的管理策略。 一、智能指針類別 智

智能指針原理實現(2)- unique_ptr

unique clas 結束 基礎 無法 body 智能指針 周期 文件 只允許基礎指針的一個所有者。 可以移到新所有者(具有移動語義),但不會復制或共享(即我們無法得到指向同一個對象的兩個unique_ptr)。 替換已棄用的 auto_ptr。 相較於 boost::s

分布式鎖原理實現方式

ack 常用 ima 個數 tar 刪除 不能 cap lock 本文轉自:http://www.hollischuang.com/archives/1716 目前幾乎很多大型網站及應用都是分布式部署的,分布式場景中的數據一致性問題一直是一個比較重要的

【數據結構】ArrayList原理實現學習總結(2)

!= 需要 但是 object count def 原理 arrays 位置 ArrayList是一個基於數組實現的鏈表(List),這一點可以從源碼中看出: transient Object[] elementData; // non-private to si

【數據結構】ArrayList原理實現學習總結

sset bsp perm arraylist 節點 article cell public arr 關於Java集合的小抄中是這樣描述的: 以數組實現。節約空間,但數組有容量限制。超出限制時會增加50%容量,用System.arraycopy()復制到新的數組,因此最好能

Svm算法原理實現

load 統計 分割 opp 出了 數組 註意 tst 簡單 Svm(support Vector Mac)又稱為支持向量機,是一種二分類的模型。當然如果進行修改之後也是可以用於多類別問題的分類。支持向量機可以分為線性核非線性兩大類。其主要思想為找到空間中的一個