Python輕量級(jí)搜索工具Whoosh的使用教程
本文將簡(jiǎn)單介紹Python中的一個(gè)輕量級(jí)搜索工具Whoosh,并給出相應(yīng)的使用示例代碼。
Whoosh簡(jiǎn)介
Whoosh由Matt Chaput創(chuàng)建,它一開(kāi)始是一個(gè)為Houdini 3D動(dòng)畫(huà)軟件包的在線文檔提供簡(jiǎn)單、快速的搜索服務(wù)工具,之后便慢慢成為一個(gè)成熟的搜索解決工具并已開(kāi)源。
Whoosh純由Python編寫(xiě)而成,是一個(gè)靈活的,方便的,輕量級(jí)的搜索引擎工具,現(xiàn)在同時(shí)支持Python2、3,其優(yōu)點(diǎn)如下:
- Whoosh純由Python編寫(xiě)而成,但很快,只需要Python環(huán)境即可,不需要編譯器;
- 默認(rèn)使用 Okapi BM25F排序算法,也支持其他排序算法;
- 相比于其他搜索引擎,Whoosh會(huì)創(chuàng)建更小的index文件;
- Whoosh中的index文件編碼必須是unicode;
- Whoosh可以?xún)?chǔ)存任意的Python對(duì)象。
Whoosh的官方介紹網(wǎng)站為:https://whoosh.readthedocs.io/en/latest/intro.html。相比于ElasticSearch或者Solr等成熟的搜索引擎工具,Whoosh顯得更輕便,操作更簡(jiǎn)單,可以考慮在小型的搜索項(xiàng)目中使用。
Index & query
對(duì)于熟悉ES的人來(lái)說(shuō),搜索的兩個(gè)重要的方面為mapping和query,也就是索引的構(gòu)建以及查詢(xún),背后是復(fù)雜的索引儲(chǔ)存、query解析以及排序算法等。如果你有ES方面的經(jīng)驗(yàn),那么,對(duì)于Whoosh是十分容易上手的。
按照筆者的理解以及Whoosh的官方文檔,Whoosh的入門(mén)使用主要是index以及query。搜索引擎的強(qiáng)大功能之一在于它能夠提供全文檢索,這依賴(lài)于排序算法,比如BM25,也依賴(lài)于我們?cè)鯓觾?chǔ)存字段。因此,index作為名詞時(shí),是指字段的索引,index作為動(dòng)詞時(shí),是指建立字段的索引。而query會(huì)將我們需要查詢(xún)的語(yǔ)句,通過(guò)排序算法,給出合理的搜索結(jié)果。
關(guān)于Whoosh的使用,在官文文檔中已經(jīng)給出了詳細(xì)的說(shuō)明,筆者在這里只給出一個(gè)簡(jiǎn)單的例子,來(lái)說(shuō)明Whoosh如何能方便地提升我們的搜索體驗(yàn)。
示例代碼
數(shù)據(jù)
本項(xiàng)目的示例數(shù)據(jù)為poem.csv,下圖為該數(shù)據(jù)集的前十行:

poem.csv
字段
根據(jù)數(shù)據(jù)集的特征,我們創(chuàng)建四個(gè)字段(fields):title, dynasty, poet, content。創(chuàng)建的代碼如下:
#?-*-?coding:?utf-8?-*- import?os from?whoosh.index?import?create_in from?whoosh.fields?import?* from?jieba.analyse?import?ChineseAnalyzer import?json #?創(chuàng)建schema,?stored為T(mén)rue表示能夠被檢索 schema?=?Schema(title=TEXT(stored=True,?analyzer=ChineseAnalyzer()), ????????????????dynasty=ID(stored=True), ????????????????poet=ID(stored=True), ????????????????content=TEXT(stored=True,?analyzer=ChineseAnalyzer()) ????????????????)
其中,ID只能為一個(gè)單元值,不能分割為若干個(gè)詞,常用于文件路徑、URL、日期、分類(lèi);
TEXT文件的文本內(nèi)容,建立文本的索引并存儲(chǔ),支持詞匯搜索;Analyzer選擇結(jié)巴中文分詞器。
創(chuàng)建索引文件
接著,我們需要?jiǎng)?chuàng)建索引文件。我們利用程序先解析poem.csv文件,并將它轉(zhuǎn)化為index,寫(xiě)入到indexdir目錄下。Python代碼如下:
#?解析poem.csv文件
with?open('poem.csv',?'r',?encoding='utf-8')?as?f:
????texts?=?[_.strip().split(',')?for?_?in?f.readlines()?if?len(_.strip().split(','))?==?4]
#?存儲(chǔ)schema信息至indexdir目錄
indexdir?=?'indexdir/'
if?not?os.path.exists(indexdir):
????os.mkdir(indexdir)
ix?=?create_in(indexdir,?schema)
#?按照schema定義信息,增加需要建立索引的文檔
writer?=?ix.writer()
for?i?in?range(1,?len(texts)):
????title,?dynasty,?poet,?content?=?texts[i]
????writer.add_document(title=title,?dynasty=dynasty,?poet=poet,?content=content)
writer.commit()
index創(chuàng)建成功后,會(huì)生成indexdir目錄,里面含有上述poem.csv數(shù)據(jù)的各個(gè)字段的索引文件。
查詢(xún)
index創(chuàng)建成功后,我們就利用進(jìn)行查詢(xún)。
比如我們想要查詢(xún)content中含有明月的詩(shī)句,可以輸入以下代碼:
#?創(chuàng)建一個(gè)檢索器
searcher?=?ix.searcher()
#?檢索content中出現(xiàn)'明月'的文檔
results?=?searcher.find("content",?"明月")
print('一共發(fā)現(xiàn)%d份文檔。'?%?len(results))
for?i?in?range(min(10,?len(results))):
????print(json.dumps(results[i].fields(),?ensure_ascii=False))
輸出結(jié)果如下:
一共發(fā)現(xiàn)44份文檔。
前10份文檔如下:
{"content": "床前明月光,疑是地上霜。舉頭望明月,低頭思故鄉(xiāng)。", "dynasty": "唐代", "poet": "李白 ", "title": "靜夜思"}
{"content": "邊草,邊草,邊草盡來(lái)兵老。山南山北雪晴,千里萬(wàn)里月明。明月,明月,胡笳一聲愁絕。", "dynasty": "唐代", "poet": "戴叔倫 ", "title": "調(diào)笑令·邊草"}
{"content": "獨(dú)坐幽篁里,彈琴?gòu)?fù)長(zhǎng)嘯。深林人不知,明月來(lái)相照。", "dynasty": "唐代", "poet": "王維 ", "title": "竹里館"}
{"content": "漢江明月照歸人,萬(wàn)里秋風(fēng)一葉身。休把客衣輕浣濯,此中猶有帝京塵。", "dynasty": "明代", "poet": "邊貢 ", "title": "重贈(zèng)吳國(guó)賓"}
{"content": "秦時(shí)明月漢時(shí)關(guān),萬(wàn)里長(zhǎng)征人未還。但使龍城飛將在,不教胡馬度陰山。", "dynasty": "唐代", "poet": "王昌齡 ", "title": "出塞二首·其一"}
{"content": "京口瓜洲一水間,鐘山只隔數(shù)重山。春風(fēng)又綠江南岸,明月何時(shí)照我還?", "dynasty": "宋代", "poet": "王安石 ", "title": "泊船瓜洲"}
{"content": "四顧山光接水光,憑欄十里芰荷香。清風(fēng)明月無(wú)人管,并作南樓一味涼。", "dynasty": "宋代", "poet": "黃庭堅(jiān) ", "title": "鄂州南樓書(shū)事"}
{"content": "青山隱隱水迢迢,秋盡江南草未凋。二十四橋明月夜,玉人何處教吹簫?", "dynasty": "唐代", "poet": "杜牧 ", "title": "寄揚(yáng)州韓綽判官"}
{"content": "露氣寒光集,微陽(yáng)下楚丘。猿啼洞庭樹(shù),人在木蘭舟。廣澤生明月,蒼山夾亂流。云中君不見(jiàn),竟夕自悲秋。", "dynasty": "唐代", "poet": "馬戴 ", "title": "楚江懷古三首·其一"}
{"content": "海上生明月,天涯共此時(shí)。情人怨遙夜,竟夕起相思。滅燭憐光滿,披衣覺(jué)露滋。不堪盈手贈(zèng),還寢夢(mèng)佳期。", "dynasty": "唐代", "poet": "張九齡 ", "title": "望月懷遠(yuǎn) / 望月懷古"}
到此這篇關(guān)于Python輕量級(jí)搜索工具Whoosh的使用教程的文章就介紹到這了,更多相關(guān)Python搜索工具Whoosh內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Python中super().__init__()測(cè)試以及理解
__init__()一般用來(lái)創(chuàng)建對(duì)象的實(shí)例變量,或一次性操作,super()用于調(diào)用父類(lèi)的方法,可用來(lái)解決多重繼承問(wèn)題,下面這篇文章主要給大家介紹了關(guān)于Python中super().__init__()測(cè)試及理解的相關(guān)資料,需要的朋友可以參考下2021-12-12
Python基礎(chǔ)之元編程知識(shí)總結(jié)
很多人不理解“元編程”是個(gè)什么東西,關(guān)于它也沒(méi)有一個(gè)十分準(zhǔn)確的定義.這篇文章要說(shuō)的是Python里的元編程,實(shí)際上也不一定就真的符合“元編程”的定義.只不過(guò)我無(wú)法找到一個(gè)更準(zhǔn)確的名字來(lái)代表這篇文章的主題,所以就借了這么一個(gè)名號(hào),需要的朋友可以參考下2021-05-05
Python使用Holoviews創(chuàng)建復(fù)雜的可視化布局
Holoviews是一個(gè)基于Python的開(kāi)源庫(kù),旨在簡(jiǎn)化數(shù)據(jù)可視化的創(chuàng)建過(guò)程,本文將為新手朋友詳細(xì)介紹如何使用Holoviews創(chuàng)建復(fù)雜的可視化布局,感興趣的可以了解下2024-11-11
Python實(shí)現(xiàn)多組數(shù)據(jù)三維繪圖系統(tǒng)
這篇文章主要為大家詳細(xì)介紹了如何利用Python實(shí)現(xiàn)多組數(shù)據(jù)三維繪圖系統(tǒng),文中的示例代碼講解詳細(xì),具有一定的學(xué)習(xí)價(jià)值,感興趣的小伙伴可以了解下2023-08-08
win10下安裝Anaconda的教程(python環(huán)境+jupyter_notebook)
Anaconda指的是一個(gè)開(kāi)源的Python發(fā)行版本,其包含了conda、Python等180多個(gè)科學(xué)包及其依賴(lài)項(xiàng)。這篇文章主要介紹了win10下安裝Anaconda(python環(huán)境+jupyter_notebook),需要的朋友可以參考下2019-10-10
Python中re正則匹配數(shù)據(jù)的實(shí)現(xiàn)
在Python中,可以使用re模塊來(lái)使用正則表達(dá)式,本文主要介紹了Python中re正則匹配數(shù)據(jù)的實(shí)現(xiàn),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2024-04-04

