日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

《深入理解Elasticsearch(原书第2版)》一2.2 查询改写

發布時間:2024/1/17 编程问答 33 豆豆
生活随笔 收集整理的這篇文章主要介紹了 《深入理解Elasticsearch(原书第2版)》一2.2 查询改写 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

本節書摘來自華章出版社《深入理解Elasticsearch(原書第2版)》一書中的第2章,第2.2節,作者[美]拉斐爾·酷奇(Rafal Ku) 馬雷克·羅戈任斯基(Marek Rogoziski),更多章節內容可以訪問云棲社區“華章計算機”公眾號查看

2.2 查詢改寫

之前我們探討了評分機制,這些知識非常珍貴,特別是當你嘗試改進查詢相關性時。我們還認為,在對查詢進行調試時,也很有必要搞清楚查詢是如何執行的。因此我們決定在本節介紹一下查詢改寫是如何工作的,為什么需要查詢改寫,以及我們應該如何控制它。
如果你之前使用過諸如前綴查詢或通配符查詢之類的查詢類型,那么你會了解這些都是基于多詞項的查詢,它們都涉及查詢改寫。Elasticsearch使用查詢改寫是出于對性能的考慮。從Lucene的角度來看,所謂的查詢改寫操作,就是把費時的原始查詢類型實例改寫成一組性能更高的查詢類型實例,從而加快查詢執行速度。查詢改寫過程對客戶端不可見,不過最好能夠知道我們可以修改查詢改寫過程。舉個例子,讓我們看看Elasticsearch是如何處理前綴查詢的。
2.2.1 前綴查詢示例
演示查詢改寫過程的最好方式莫過于通過范例深入了解該過程的內部實現機制,尤其是要去了解原始查詢中的詞項是如何被改寫成目標查詢中那些詞項的。假設我們索引了下面這些文檔中的數據:







現在我們想找出索引中所有name字段以字母j開頭的文檔。簡單起見,我們在clients索引中執行以下查詢:




這里使用了一個簡單的前綴查詢,想檢索出所有name字段以字母j開頭的文檔。我們同時也設置了查詢改寫屬性以確定執行查詢改寫的具體方法,不過現在我們跳過該參數,具體的參數值將在本章的后續部分討論。
執行前面的查詢以后,我們將得到下面的結果:





如你所見,返回結果中有3個文檔,這些文檔的name字段以字母j開頭。我們并沒有顯式設置待查詢索引的映射,因此Elasticsearch探測出了name字段的映射,并將其設置為字符串類型并進行文本分析。可使用下面的命令進行檢查:




Elasticsearch將返回類似下面的結果:


2.2.2 回到Apache Lucene
現在我們回到Lucene。如果你還記得Lucene倒排索引是如何構建的,你會指出倒排索引中包含了詞項、詞頻以及文檔指針(如果忘了,請重新閱讀1.1節)。現在我們看看之前存儲到clients索引中的數據大概是如何組織的。




Term這一列非常重要。如果我們去探究Elasticsearch和Lucene的內部實現,將會發現前綴查詢被改寫為下面這種查詢:




我們可以用Elasticsearch API來檢查重寫片段。首先,使用Explain API執行如下命令:



執行結果如下:




可以看到,Elasticsearch對name字段使用了一個詞項是joe的constant_score查詢。當然,這一步發生在Lucene中,Elasticsearch實際上只是從緩存中獲取這些詞項。這一點可以用Validate查詢API來驗證。






Elasticsearch返回的結果如下:




2.2.3 查詢改寫的屬性
當然,多詞項查詢的rewrite屬性也可以支持除了“constant_score_boolean”之外的其他取值。我們可以通過這個屬性來控制查詢在Lucene內部的改寫方式。我們可以將rewrite參數存放在代表實際查詢的JSON對象中,例如,像下面的代碼這樣:




現在讓我們來看看rewrite參數有哪些選項可以配置。
scoring_boolean:該選項將每個生成的詞項轉化為布爾查詢中的一個或從句(Boolean should clause)。這種改寫方法需要針對每個文檔都計算得分。因此,這種方法比較耗費CPU(因為要計算和保存每個詞項的得分),而且有些查詢生成了太多的詞項,以至于超出了布爾查詢默認的1024個從句的限制。默認的布爾查詢限制可以通過設置Elasticsearch.yml文件的index.query.bool.max_clause_count屬性來修改。用戶需謹記,改寫后的布爾查詢的從句數越多,查詢性能越低。
constant_score_boolean:該選項與前面提到過的scoring_boolean類似,但是CPU耗費更少,這是因為并不計算每個從句的得分,而是每個從句得到一個與查詢權重相同的一個常數得分,默認情況下等于1,我們也可以通過設置查詢權重來改變這個默認值。與scoring_boolean類似,該選項也有布爾從句數的限制。
constant_score_filter:正如Lucene的Javadocs描述的那樣,該選項按如下方式改寫原始查詢—通過順序遍歷每個詞項來創建一個私有的過濾器,標記所有包含這個詞項的文檔。命中的文檔被賦予一個與查詢權重相同的常量得分。當命中詞項數或文檔數較大時,該方法比scoring_boolean 和constant_score_boolean執行速度更快。
top_terms_N:該選項將每個生成的詞項轉化為布爾查詢中的一個或從句,并保存計算出來的查詢得分。與scoring_boolean不同之處在于,該方法只保留最佳的N個詞項,以避免觸及布爾從句數的限制,并提升查詢整體性能。
top_terms_boost_N:該選項與top_terms_N類似,不同之處在于它的文檔得分不是通過計算得出的,而是被設置為跟查詢權重(boost)一致,默認值為1。
 當rewrite屬性設置為constant_score_auto或者沒有設置時,Elasticsearch會根據查詢的類型及其構造方式來決定是使用constant_score_filter還是constant_score_boolean。
現在,讓我們再看一個例子。如果我們想在范例查詢中使用top_terms_N選項,并且N的值設置為2,那么查詢看起來與下面的代碼類似:




從Elasticsearch返回的結果中可以看出,和我們之前使用的查詢不同,這里的文檔得分都不等于1.0。






這是因為top_terms_N需要保留得分最高的N個詞項。
結束本節之前,讀者應該會產生一個疑問,我們如何決定何時采用何種查詢改寫方法?該問題的答案更多地取決于您的應用場景。簡單來說,如果您能接受較低的精度和相關性(但是追求更高的性能),那么可以采用top-N查詢改寫方法。如果您需要更高的查詢精度和更好的相關性(同時可以接受較低的性能),那么應該采用布爾方法。

總結

以上是生活随笔為你收集整理的《深入理解Elasticsearch(原书第2版)》一2.2 查询改写的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。