ES基於Lucene開發,因此也繼承了Lucene的一些多樣化的查詢,比如本篇說的Span Query跨度查詢,就是基於Lucene中的SpanTermQuery以及其他的Query封裝出的DSL,接下來就看一下這些DSL都如何使用吧!
更多翻譯參考:Elasticsearch知識匯總
span_term查詢
這個查詢如果單獨使用,效果跟term查詢差不多,但是一般還是用於其他的span查詢的子查詢。
用法也很簡單,只需要指定查詢的字段即可:
{ "span_term" : { "user" : "kimchy" } }
另外,還可以指定查詢出的分值倍數:
{ "span_term" : { "user" : { "value" : "kimchy", "boost" : 2.0 } } }
span_multi查詢
span_multi可以包裝一個multi_term查詢,比如wildcard,fuzzy,prefix,term,range或者regexp等等,把他們包裝起來當做一個span查詢。
用法也比較簡單,內部嵌套一個普通的multi_term查詢就行了:
{ "span_multi":{ "match":{ "prefix" : { "user" : { "value" : "ki" } } } } }
也可以使用boost乘以分值,以改變查詢結果的分數:
{ "span_multi":{ "match":{ "prefix" : { "user" : { "value" : "ki", "boost" : 1.08 } } } } }
span_first查詢
這個查詢用於確定一個單詞相對於起始位置的偏移位置,舉個例子:
如果一個文檔字段的內容是:“hello,my name is tom”,我們要檢索tom,那么它的span_first最小應該是5,否則就查找不到。
使用的時候,只是比span_term多了一個end界定而已:
{ "span_first" : { "match" : { "span_term" : { "user" : "kimchy" } }, "end" : 3 } }
span_near查詢
這個查詢主要用於確定幾個span_term之間的距離,通常用於檢索某些相鄰的單詞,避免在全局跨字段檢索而干擾最終的結果。
查詢主要由兩部分組成,一部分是嵌套的子span查詢,另一部分就是他們之間的最大的跨度
{ "span_near" : { "clauses" : [ { "span_term" : { "field" : "value1" } }, { "span_term" : { "field" : "value2" } }, { "span_term" : { "field" : "value3" } } ], "slop" : 12, "in_order" : false, "collect_payloads" : false } }
上面的例子中,value1,value2,value3最長的跨度不能超過12.
span_or查詢
這個查詢會嵌套一些子查詢,子查詢之間的邏輯關系為 或
{ "span_or" : { "clauses" : [ { "span_term" : { "field" : "value1" } }, { "span_term" : { "field" : "value2" } }, { "span_term" : { "field" : "value3" } } ] } }
span_not查詢
這個查詢相對於span_or來說,就是排除的意思。不過它內部有幾個屬性,include用於定義包含的span查詢;exclude用於定義排除的span查詢
{ "span_not" : { "include" : { "span_term" : { "field1" : "hoya" } }, "exclude" : { "span_near" : { "clauses" : [ { "span_term" : { "field1" : "la" } }, { "span_term" : { "field1" : "hoya" } } ], "slop" : 0, "in_order" : true } } } }
span_containing查詢
這個查詢內部會有多個子查詢,但是會設定某個子查詢優先級更高,作用更大,通過關鍵字little和big來指定。
{ "span_containing" : { "little" : { "span_term" : { "field1" : "foo" } }, "big" : { "span_near" : { "clauses" : [ { "span_term" : { "field1" : "bar" } }, { "span_term" : { "field1" : "baz" } } ], "slop" : 5, "in_order" : true } } } }
span_within查詢
這個查詢與span_containing查詢作用差不多,不過span_containing是基於lucene中的SpanContainingQuery,而span_within則是基於SpanWithinQuery。