最近在作一個項目,尋遍了 Node 開源社區竟然沒有發現一個好用的敏感詞過濾庫,有那麼幾個庫外觀上看起來彷佛還不錯,用起來卻一塌糊塗,震驚有餘,失望至極。因而花了一天時間本身擼了一個庫,庫名叫 fastscan,這是個人第一個 Node 開源項目,它也能夠用於瀏覽器環境。fastscan 基於廣爲人知的 ahocorasick 高性能字符串匹配算法。java
項目地址:github.com/pyloque/fas…node
演示地址:pyloque.github.com/fastscangit
考慮到太多的違禁詞彙,因此縮小化顯示,縮小到讓你看不清楚。若是想看清楚一點,仍是去演示地址裏面看吧。消滅敏感詞是每一個公民責無旁貸的責任!你不站崗我不站崗,誰保衛咱祖國誰來保衛家!讀者們大家要是敢舉報,看我不砍死你!github
# 安裝到當前項目
npm install --save fastscan
# 寫了很多單元測試,感興趣運行一下
npm test
複製代碼
import FastScanner from fastscan
var words = ["今日頭條","微信", "支付寶"]
var scanner = new FastScanner(words)
var content = "今日頭條小程序終於來了,這是繼微信、支付寶、百度後,第四個推出小程序功能的App。貓眼電影率先試水,出如今今日頭條。"
var offWords = scanner.search(content)
console.log(offWords)
var hits = scanner.hits(content)
console.log(hits)
-------------
[ [ 0, '今日頭條' ], [ 15, '微信' ], [ 18, '支付寶' ], [ 53, '今日頭條' ] ]
{ '今日頭條': 2, '微信': 1, '支付寶': 1 }
複製代碼
options = {quick: false, longest: false}
複製代碼
項目代碼使用原生的 js 實現,我開始很是擔憂詞彙樹的構建速度會不會太慢。經測試後發現雖然性能不算太快,不過也不是太差,對於絕大多數項目來講已經綽綽有餘了。我分別測試了構造 20000~100000 個詞彙的樹結構,每一個詞彙隨機在 10~20之間,耗時狀況以下算法
20000 words | 385ms |
---|---|
40000 words | 654ms |
60000 words | 1108ms |
80000 words | 1273ms |
100000 words | 1659ms |
若是你的詞彙比較短小,構建樹的速度還會更快。npm
查詢性能我並不擔憂,由於 ahocorasick 算法在詞彙長度較短的狀況下複雜度是 O(n),性能和被過濾內容的長度乘線性變化。下面我使用 100000 詞彙量構建的樹分別對 20000 ~ 100000字的內容進行了過濾,耗時狀況以下小程序
20000 words | 12ms |
---|---|
40000 words | 28ms |
60000 words | 35ms |
80000 words | 49ms |
100000 words | 51ms |
fastscan 能夠作到以迅雷不及掩耳的速度掃遍一幅 10w 字的長文,10w 大概就是一部中篇小說的長度了。若是你要掃百萬字的長篇小說,那仍是建議你分章分節來掃吧。瀏覽器
內存佔用也是須要考慮的點,內存對於 Node 程序來講原本就很是有限,若是由於敏感詞樹佔據了太大的內存那是很是要不得的大問題。因此我也對內存佔用進行了測試,下面是測試的結果bash
0 words | 14M |
---|---|
20000 words | 81M |
40000 words | 135M |
60000 words | 184M |
80000 words | 234M |
100000 words | 277M |
詞彙量不是太大的話,這樣的內存佔用仍是能夠接受的。若是你對內存佔用不滿意,那就只能使用 Node 的 C 語言擴展來打造更高性能的庫了,考慮到成本問題,恕我目前無能爲力。微信
注:不得不說,node 社區發佈開源類庫太方便了,npm login && npm publish 輕鬆搞定。我的以爲這大概就是 node 輪子多的罪魁禍首。對比以前發佈 java 社區開源項目,感受本身頭髮都快掉光了,造輪子比發佈輪子還要輕鬆。
若是讀者比較關心算法的原理和細節,請關注個人公衆號「碼洞」,後續我會編寫相關文章來仔細講解算法的原理,以及對 fastscan 項目代碼的剖析。