solr高級查詢——facet分面

1.簡述

1.1 概念

分面搜索也稱爲分面瀏覽,他容許用戶在執行搜索時,根據文檔的一個或者多個方面(即分面)對搜索結果進行細分。用戶經過選擇不一樣的過濾器來探索搜索結果。html

1.2 應用場景

在搜索求職網站時,咱們但願對搜索結果按照城市、工做類別、行業甚至是公司名稱等選項進行篩選。通常來講,這些過濾選項不只展現了每一個分面的可用值,並且統計了每一個分面值匹配到的搜索結果數。因爲屏幕只能爲每一個分面顯示有限數量的值,搜索引擎一般會根據熱門程度(文檔匹配最多的)對分面值進行排序。讓用戶無需查看每一個搜索結果,就能夠快速的搜索結果的總體狀況。apache

1.3 功能

solr的分面功能將動態元數據隨搜索結果一塊兒返回。分面最基本的形式是展現字段中的每個惟一值和其對匹配的文檔出現的次數(注意:不是匹配的文檔數量而是匹配的文檔出現次數),這個字段來自文檔的共享屬性,例如:類目列表。緩存

solr提供了許多高級分面功能,包括基於函數、值區間以及任意查詢的搜索結果分面。solr還支持層級分面多維分面多選分面,其中多選分面能夠對那些以及從搜索結果中過濾掉的文檔進行分面計數。electron

2.搜索結果預覽

分面搜索通常有兩個步驟組成:分面的計算與顯示,即「分面返回」,有時簡稱爲分面;用戶選擇一個或者多個分面值,對搜索結果進行過濾,即「分面選擇「或者」分面過濾「ide

假設對一組參觀文檔進行搜索,你可能但願在用戶界面放置一些分面來做爲導航元素,以下圖,當查詢」hamburger「時返回的結果:函數

圖片地址

如上圖,每一個類別(餐廳類型、州、價格區間及城市)都被視爲一個分面。分面能夠當作是對搜索結果的一個信息切片。這個界面相似於咱們在購物網站搜索某一件商品後,而後根據商品的各類屬性進行進一步的篩選。網站

3.字段分面

字段分面是最多見的分面形式。執行搜索時,根據查詢請求返回特定字段中找到惟一值以及找到文檔數。字段分麪包括:單值分面多值分面 。其中單值分面中每一個惟一值都會被檢視,並返回每一個值對應的文檔數,因爲每一個文檔只須要一個值,所以此值的統計數等同於文檔總數。多值分面中,多個標籤可能對應同一個文檔,所以大多數文檔被不止一個分面值計數過。ui

對於多值分面,Solr開發者建立了一個單獨的字段,在該字段中放入特定內容的副本,該字段僅用於分面目的,這樣原始文本就可以以分面的形式保留。搜索引擎

3.1 字段分面參數

Solr參數 可能取值 說明
facet true,false 對當前搜索是否啓用分面
facet.field 任意索引字段名稱 肯定對那個字段進行分面,可屢次指定
facet.sort index,count 排序方式:根據最大出現次數(count)或者索引(index)的詞典序排序
facet.limit 整數>=-1 返回多少個惟一分面值
facet.mincount 整數>=0 在分面返回以前設置必須出現最少文檔數,默認爲1.
facet.method enum,fc,fcs enum方法循環遍歷索引中全部詞項,計算這些詞項與查詢的交集,fc(字段緩存)方法對與查詢匹配的文檔進行循環,在這些文檔中找到詞項,fc是除了布爾值以外的默認方法。fcs方法爲單值字符串調用每一個片斷緩存。
facet.enum.cache.minDf 整數>=0 在filterCache用於詞項以前,指定與蓋茨匹配的最小文檔數
facet.prefix 任意字符串 指定查詢到詞項的前綴
facet.missing true,false 是否返回不包含分面字段的文檔計數
facet.offset 整數>=0 經過分面值進行分頁。offset指定跳過最開始的幾個值,昨晚後面分面的替代
facet.threads 整數 當執行多個字段分面時指定的線程數。默認是0,負數表明爲每一個字段生成一個線程

其中,能夠基於字段進行指定的有:facet.limit,facet.mincount,facet.method,facet.enum.cache.minDf,使用格式爲: f..= eg:線程

requestUrl:

http://192.168.10.125:8983/solr/techproducts/select?q=*:*&
facet=true&                // 開啓facet
facet.limit=6&             // 默認全部facet展現六條數據
facet.field=weight&        // facet字段爲weight
f.weight.facet.limit=4&    // 指定weight字段只顯示4條
f.weight.facet.sort=index& // 指定weight字段爲字典序排序
facet.field=cat&            
f.cat.facet.mincount=2     // 最少統計數爲2

response:

"facet_counts":{
    "facet_queries":{},
    "facet_fields":{
      "weight":[            
        "2.0",1,
        "4.0",1,
        "5.5",1,
        "6.4",1],
      "cat":[
        "electronics",12,
        "currency",4,
        "memory",3,
        "connector",2,
        "graphics card",2,
        "hard drive",2]},
        "facet_ranges":{},
    "facet_intervals":{},
    "facet_heatmaps":{}}}

如結果所示:weight排序方式爲字典序,cat排序方式爲默認的count,即按照統計數量大小降序;weight展現了4條記錄,cat未特殊指定數量,展現了默認的6條數據;cat指定最少統計數爲2,weight未指定因此也展現出了爲1的。

4. 查詢分面

將某一個字段的值分爲多個區間,查詢每一個區間對應的數量。例如,咱們想知道商品在區間[,200]、[200,400]、[400,600]、[600,]中,每一個區間對應的數量,則可使用查詢分面。格式爲:facet.query=field:[start+TO+end],其中"["表明閉區間,"{"表明開區間,"+"表明空格,注意"TO"必須爲大寫。

http://192.168.10.125:8983/solr/techproducts/select?q=*:*&rows=0&facet=true&
facet.query=price:[*+TO+200}&
facet.query=price:[200+TO+400}&
facet.query=price:[400+TO+600}&
facet.query=price:[600+TO+*]
"facet_counts":{
    "facet_queries":{
      "price:[* TO 200}":9,
      "price:[200 TO 400}":4,
      "price:[400 TO 600}":1,
      "price:[600 TO *]":2},
    "facet_fields":{},
    "facet_ranges":{},
    "facet_intervals":{},
    "facet_heatmaps":{}}}

5.區間分面

區間分面將數值和日期字段分紅一些區間,以便於solr返回各個區間以及他們包含的文檔數。建立多個不一樣的查詢分面來表示多個區間值的作法能夠經過區間分面進行替代。

對上面的例子可經過如下方式實現:

http://192.168.10.125:8983/solr/techproducts/select?q=*:*&rows=0&facet=true&
facet.range=price&              // 分區字段
f.price.facet.range.start=0.0&  // 分區起始值
f.price.facet.range.end=1000.0& // 分區結束值
f.price.facet.range.gap=200     // 分區步長

可獲得一樣的統計結果

"facet_counts":{
    "facet_queries":{},
    "facet_fields":{},
    "facet_ranges":{
      "price":{
        "counts":[
          "0.0",9,
          "200.0",4,
          "400.0",1,
          "600.0",1,
          "800.0",0],
        "gap":200.0,
        "start":0.0,
        "end":1000.0}},
    "facet_intervals":{},
    "facet_heatmaps":{}}}

6.Pivot(Decision Tree)Faceting 決策樹分面

經過pivot關鍵字定義樹狀結構的分面結果,在一個分面結果中能夠包含另外一個分面結果

http://localhost:8983/solr/techproducts/select?q=*:*&
facet.pivot=cat,popularity,inStock&
facet.pivot=popularity,cat&
facet=true&
facet.field=cat&
facet.limit=5&
rows=0&
facet.pivot.mincount=2

分面結果:

{  "facet_counts":{
    "facet_queries":{},
    "facet_fields":{
      "cat":[
        "electronics",14,
        "currency",4,
        "memory",3,
        "connector",2,
        "graphics card",2]},
    "facet_dates":{},
    "facet_ranges":{},
    "facet_pivot":{
      "cat,popularity,inStock":[{
          "field":"cat",
          "value":"electronics",
          "count":14,
          "pivot":[{
              "field":"popularity",
              "value":6,
              "count":5,
              "pivot":[{
                  "field":"inStock",
                  "value":true,
                  "count":5}]}]
}]}}}

7.其餘

  1. 可在分面值查詢請求上添加過濾器,例如&fq=price:[*+TO100] ,將過濾掉對[0,100]的統計.
  2. 多值過濾時須要使用雙引號,例如fq=city:"china beijing",若是字符串中有特殊符號須要進行轉意,例如:fq=name:"the \"in\" crowd" .
  3. 經過key關鍵字給分面字段重命名,例如facet.query={!key="兩百如下"}price :[*+TO+200],則facet_query中的顯示結果將由"price:[* TO 200}":9,變爲"price:[兩百如下}":9,
  4. 經過tag和ex標記忽略過濾器。用tag定義一個過濾器fq={!tag="tag1"}state:California,定一個了一個隊state字段的過濾器,並命名爲tag1,而後在facet的field定義時使用tag標籤facet.field={!ex=tag1}state,這樣state分面就會忽略標記爲tag1的過濾器,也就是這個過濾器對state字段不進行過濾。

參考

http://lucene.apache.org/solr/guide/7_0/faceting.html#pivot-decision-tree-faceting

相關文章
相關標籤/搜索