一、什麼是拼寫糾錯
拼寫糾錯就是搜尋引擎可以智慧的感知使用者輸入關鍵字的錯誤,並使用糾正過的關鍵字進行搜尋展示給使用者;拼寫糾錯是一種改善使用者體驗的功能;
elasticsearch提供了以下不同型別的suggester來完成拼寫糾錯和自動完成功能;
term suggester主要針對單個的term分詞進行糾正的場景;
phrase suggester主要針對整個短語的拼寫糾正場景;
completion suggester主要提供一種快速高效的自動提示功能;
二、Term Suggester基於單個詞的拼寫糾錯
Term Suggester會將使用者輸入的text進行解析分解成單個的word,然後針對每個word進行糾錯;
elasticsearch的suggester請求的還是_search端點,要傳送一個Term suggester請求,我們需要
1.在body中新增suggest欄位;
2.指定我們的suggest的名字,我們可以使用不同的名字同時進行多個拼寫糾錯, 其最終的執行結果在response中也會使用這個名字進行區分;
3.通過text欄位指定要糾正的文字;
4.指定要使用的suggester型別,這裡使用term;
5.指定要在哪個欄位上進行拼寫糾錯;
POST blogs/_search
{
"suggest": {
"my_sug": {
"text": "hots vlna",
"term": {
"field": "content"
}
}
}
}
elasticsearch返回結果中的suggest部分包含對應的結果;
不同名字的suggester在返回結果中作為suggest物件的欄位,其作為陣列承載每個text分詞的建議結果;
每個原始的word作為一個物件,物件會記錄原始word的基本資訊及所有的建議詞;
每個建議詞物件會包含文字、打分、出現頻率;
{
"suggest" : {
"my_sug" : [
{
"text" : "hots",
"offset" : 0,
"length" : 4,
"options" : [
{
"text" : "host",
"score" : 0.75,
"freq" : 109
},
{
"text" : "http",
"score" : 0.5,
"freq" : 235
},
{
"text" : "https",
"score" : 0.5,
"freq" : 9
},
{
"text" : "hours",
"score" : 0.5,
"freq" : 6
},
{
"text" : "hole",
"score" : 0.5,
"freq" : 5
}
]
},
{
"text" : "vlna",
"offset" : 5,
"length" : 4,
"options" : [
{
"text" : "vlan",
"score" : 0.75,
"freq" : 200
},
{
"text" : "vpna",
"score" : 0.75,
"freq" : 3
},
{
"text" : "vlan1",
"score" : 0.5,
"freq" : 111
},
{
"text" : "vlans",
"score" : 0.5,
"freq" : 11
},
{
"text" : "vlan8",
"score" : 0.5,
"freq" : 10
}
]
}
]
}
}
三、Term Suggester的通用配置選項
Term Suggester基於編輯距離來計算字串的相似性;如果一個建議詞通過更少字元的改變、新增、刪除來轉變成原始的字串,那麼這就是一個更好的建議詞;例如host通過變換t和s的位置變成hots,則二者的編輯距離是1;
text既可以在suggest裡邊單獨設定,也可以在全域性設定;
POST blogs/_search
{
"suggest": {
"text": "hots vlna",
"content_sug": {
"term": {
"field": "content"
}
},
"title_sug": {
"term": {
"field": "title"
}
}
}
}
analyzer對text設定的文字進行analyse處理,預設使用field欄位的search analyzer;
POST blogs/_search
{
"suggest": {
"my_sug": {
"text": "hots vlna",
"term": {
"analyzer":"standard",
"field": "content"
}
}
}
}
size設定每個word返回的建議詞的數量,預設是5個;
POST blogs/_search
{
"suggest": {
"my_sug": {
"text": "hots vlna",
"term": {
"analyzer":"standard",
"field": "content",
"size":6
}
}
}
}
sort設定每個word對應的建議詞的排序方式,由於每個建議詞只包含text、score、freq,這就涉及以哪個欄位先排序;
score,先使用score排序,後使用freq排序,最後使用建議詞排序;
frequency,先使用freq排序,後使用score排序,最後使用建議詞排序;
POST blogs/_search
{
"suggest": {
"my_sug": {
"text": "hots",
"term": {
"field": "content",
"sort":"frequency"
}
}
}
}
{
"suggest" : {
"my_sug" : [
{
"text" : "hots",
"offset" : 0,
"length" : 4,
"options" : [
{
"text" : "http",
"score" : 0.5,
"freq" : 235
},
{
"text" : "host",
"score" : 0.75,
"freq" : 109
},
{
"text" : "https",
"score" : 0.5,
"freq" : 9
},
{
"text" : "hours",
"score" : 0.5,
"freq" : 6
},
{
"text" : "hole",
"score" : 0.5,
"freq" : 5
}
]
}
]
}
}
suggest_mode,主要控制針對什麼樣的詞會返回建議詞,以及返回那些建議詞;
missing,預設的選項,只有輸入的詞在對應欄位的分詞中不存在,才有可能返回建議詞;
popular,只返回在更多的文件中出現的建議詞;
always,任何的建議詞都可以返回;
由於vlan322在欄位content裡已經存在,使用missing模式沒有任何返回結果;
POST blogs/_search
{
"suggest": {
"my_sug": {
"text": "vlan322",
"term": {
"field": "content",
"suggest_mode":"missing"
}
}
}
}
{
"suggest" : {
"my_sug" : [
{
"text" : "vlan322",
"offset" : 0,
"length" : 7,
"options" : [ ]
}
]
}
}
使用popular模式則會返回對應的建議詞;
POST blogs/_search
{
"suggest": {
"my_sug": {
"text": "vlan322",
"term": {
"field": "content",
"suggest_mode":"popular"
}
}
}
}
{
"suggest" : {
"my_sug" : [
{
"text" : "vlan322",
"offset" : 0,
"length" : 7,
"options" : [
{
"text" : "vlan0022",
"score" : 0.71428573,
"freq" : 5
},
{
"text" : "vlan30",
"score" : 0.6666666,
"freq" : 14
},
{
"text" : "vlan20",
"score" : 0.6666666,
"freq" : 7
},
{
"text" : "vlan.2",
"score" : 0.6666666,
"freq" : 6
},
{
"text" : "vlan12",
"score" : 0.6666666,
"freq" : 6
}
]
}
]
}
}
四、Term Suggester的專有配置選項
max_edits,主要控制可以包含的最大編輯距離的建議詞,可以取值1或者2,預設值為2;
POST blogs/_search
{
"suggest": {
"my_sug": {
"text": "vlan322",
"term": {
"field": "content",
"max_edits":1
}
}
}
}
{
"suggest" : {
"my_sug" : [
{
"text" : "htpt",
"offset" : 0,
"length" : 4,
"options" : [
{
"text" : "http",
"score" : 0.75,
"freq" : 235
}
]
}
]
}
}
prefix_length,主要控制原始word的開頭多少個字元不參與拼錯糾正,預設值為1,提高這個值可以提高效能;
POST blogs/_search
{
"suggest": {
"my_sug": {
"text": "vlan322",
"term": {
"field": "content",
"prefix_length":2
}
}
}
}
{
"suggest" : {
"my_sug" : [
{
"text" : "htpt",
"offset" : 0,
"length" : 4,
"options" : [ ]
}
]
}
}
min_word_length,控制建議詞的最小字元長度,預設是4;
POST blogs/_search
{
"suggest": {
"my_sug": {
"text": "vlan32",
"term": {
"field": "content",
"min_word_length":7
}
}
}
}
shard_size,主要控制每個分片返回的建議詞的數量,通過增大這個設定數量可以提高建議詞的準確性,但是可能會降低整體的效能;預設值跟size保持一致;
POST blogs/_search
{
"suggest": {
"my_sug": {
"text": "vlan32",
"term": {
"field": "content",
"shard_size":3,
"size":10,
}
}
}
}
{
"suggest" : {
"my_sug" : [
{
"text" : "vlan32",
"offset" : 0,
"length" : 6,
"options" : [
{
"text" : "vlan30",
"score" : 0.8333333,
"freq" : 14
},
{
"text" : "vlan.2",
"score" : 0.8333333,
"freq" : 6
},
{
"text" : "vlan12",
"score" : 0.8333333,
"freq" : 6
}
]
}
]
}
}
max_inspections,通過與shards_size相乘控制shard級別檢測可選建議詞的數量,預設值5;沒有測試出具體的效果;
min_doc_freq,主要控制返回建議詞至少在index中至少多個document中出現過,預設值為0,通過提高這個值可以提高準確率,可以設定具體的值也可以設定百分比;這是一個基於shard level配置選項;
POST blogs/_search
{
"suggest": {
"my_sug": {
"text": "vlan32",
"term": {
"field": "content",
"min_doc_freq":3
}
}
}
}
{
"suggest" : {
"my_sug" : [
{
"text" : "vlan32",
"offset" : 0,
"length" : 6,
"options" : [
{
"text" : "vlan30",
"score" : 0.8333333,
"freq" : 14
},
{
"text" : "vlan.2",
"score" : 0.8333333,
"freq" : 6
},
{
"text" : "vlan12",
"score" : 0.8333333,
"freq" : 6
},
{
"text" : "vlan2",
"score" : 0.8,
"freq" : 8
},
{
"text" : "vlan10",
"score" : 0.6666666,
"freq" : 55
}
]
}
]
}
}
max_term_freq,主要控制建議詞在文件中出現的最多的次數,可以設定具體數值和百分比;預設值0.01f;降低這個值可以排除更多的建議詞從而提高效能;這個也是shard級別的配置;
POST blogs/_search
{
"suggest": {
"my_sug": {
"text": "vlan32",
"term": {
"field": "content",
"max_term_freq":1
}
}
}
}
string_distance,設定計算編輯距離的具體演算法,可選值有internal、damerau_levenshtein、levenshtein、jaro_winkler、ngram;