1抡诞、query string基礎語法
GET /test_index/test_type/_search?q=test_field:test//查詢test_field中有test的
GET /test_index/test_type/_search?q=+test_field:test//必須包含斟叼,和上面一樣
GET /test_index/test_type/_search?q=-test_field:test//不包含
2、_all metadata的原理和作用
GET /test_index/test_type/_search?q=test
直接可以搜索所有的field丹莲,任意一個field包含指定的關鍵字就可以搜索出來光坝。我們在進行中搜索的時候,難道是對document中的每一個field都進行一次搜索嗎甥材?不是的
es中的_all元數(shù)據(jù)盯另,在建立索引的時候,我們插入一條document洲赵,它里面包含了多個field土铺,此時,es會自動將多個field的值板鬓,全部用字符串的方式串聯(lián)起來,變成一個長的字符串究恤,作為_all field的值俭令,同時建立索引
后面如果在搜索的時候,沒有對某個field指定搜索部宿,就默認搜索_all field抄腔,其中是包含了所有field的值的
舉個例子
{
??"name": "jack",
??"age": 26,
??"email": "jack@sina.com",
??"address": "guamgzhou"
}
"jack 26 jack@sina.com guangzhou",作為這一條document的_all field的值理张,同時進行分詞后建立對應的倒排索引
3赫蛇、初識搜索引擎_用一個例子告訴你mapping到底是什么
插入幾條數(shù)據(jù),讓es自動為我們建立一個索引
PUT /website/article/1
{
??"post_date": "2017-01-01",
??"title": "my first article",
??"content": "this is my first article in this website",
??"author_id": 11400
}
PUT /website/article/2
{
??"post_date": "2017-01-02",
??"title": "my second article",
??"content": "this is my second article in this website",
??"author_id": 11400
}
PUT /website/article/3
{
??"post_date": "2017-01-03",
??"title": "my third article",
??"content": "this is my third article in this website",
??"author_id": 11400
}
嘗試各種搜索
GET /website/article/_search?q=2017 3條結果 ????????????
GET /website/article/_search?q=2017-01-01 ??????? 3條結果
GET /website/article/_search?q=post_date:2017-01-01 ?? 1條結果
GET /website/article/_search?q=post_date:2017 ???????? 1條結果
查看es自動建立的mapping雾叭,帶出什么是mapping的知識點:
自動或手動為index中的type建立的一種數(shù)據(jù)結構和相關配置悟耘,簡稱為mapping
dynamic mapping,自動為我們建立index织狐,創(chuàng)建type暂幼,以及type對應的mapping筏勒,mapping中包含了每個field對應的數(shù)據(jù)類型,以及如何分詞等設置旺嬉。
查看mapping
GET /website/_mapping/article??
信息
{
??"website": {
????"mappings": {
??????"article": {
????????"properties": {
??????????"author_id": {
????????????"type": "long"
??????????},
??????????"content": {
????????????"type": "text",
????????????"fields": {
??????????????"keyword": {
????????????????"type": "keyword",
????????????????"ignore_above": 256
??????????????}
????????????}
??????????},
??????????"post_date": {
????????????"type": "date"
??????????},
??????????"title": {
????????????"type": "text",
????????????"fields": {
??????????????"keyword": {
????????????????"type": "keyword",
????????????????"ignore_above": 256
??????????????}
????????????}
??????????}
????????}
??????}
????}
??}
}
搜索結果為什么不一致管行,因為es自動建立mapping的時候,設置了不同的field不同的data type邪媳。不同的data type的分詞捐顷、搜索等行為是不一樣的。所以出現(xiàn)了_all field和post_date field的搜索表現(xiàn)完全不一樣雨效。(先看4-6的一些知識點后就知道為什么了)
4迅涮、精確匹配與全文搜索的對比分析
1、exact value精準批配
2017-01-01设易,exact value逗柴,搜索的時候,必須輸入2017-01-01顿肺,才能搜索出來
如果你輸入一個01戏溺,是搜索不出來的
2、full text全文搜索
(1)縮寫 vs. 全程:cn vs. china
(2)格式轉化:like liked likes
(3)大小寫:Tom vs tom
(4)同義詞:like vs love
就不是說單純的只是匹配完整的一個值屠尊,而是可以對值進行拆分詞語后(分詞)進行匹配旷祸,也可以通過縮寫、時態(tài)讼昆、大小寫托享、同義詞等進行匹配
5、倒排索引核心原理快速揭秘
doc1:I really liked my small dogs, and I think my mom also liked them.
doc2:He never liked any dogs, so I hope that my mom will not expect me to liked him.
分詞浸赫,初步的倒排索引的建立
word?doc1??doc2
liked?*??*
small?*???
dogs?*???
mom?*??*
演示了一下倒排索引最簡單的建立的一個過程
搜索mother like little dog闰围,不可能有任何結果
這個是不是我們想要的搜索結果?既峡?羡榴?絕對不是,因為在我們看來运敢,mother和mom有區(qū)別嗎校仑?同義詞,都是媽媽的意思传惠。like和liked有區(qū)別嗎迄沫?沒有,都是喜歡的意思卦方,只不過一個是現(xiàn)在時羊瘩,一個是過去時。little和small有區(qū)別嗎?同義詞困后,都是小小的乐纸。dog和dogs有區(qū)別嗎?狗摇予,只不過一個是單數(shù)汽绢,一個是復數(shù)。
normalization侧戴,建立倒排索引的時候宁昭,會執(zhí)行一個操作,也就是說對拆分出的各個單詞進行相應的處理酗宋,以提升后面搜索的時候能夠搜索到相關聯(lián)的文檔的概率
worddoc1doc2?
liked**liked --> like
small*?small --> little
dogs*?dogs --> dog
mom**?
這樣后在執(zhí)行上面的操作就可以doc1和doc2都會搜索出來
6积仗、分詞器
(1)、什么是分詞器
切分詞語蜕猫,normalization(提升recall召回率)normalization(翻譯是標準化)
給你一段句子寂曹,然后將這段句子拆分成一個一個的單個的單詞,同時對每個單詞進行normalization(時態(tài)轉換回右,單復數(shù)轉換)隆圆,分瓷器
recall,召回率:搜索的時候翔烁,增加能夠搜索到的結果的數(shù)量
character filter:在一段文本進行分詞之前渺氧,先進行預處理,比如說最常見的就是蹬屹,過濾html標簽(<span>hello<span> --> hello)侣背,& --> and(I&you --> I and you)
tokenizer:分詞,hello you and me --> hello, you, and, me
token filter:lowercase慨默,stop word贩耐,synonymom,dogs --> dog厦取,liked --> like憔杨,Tom --> tom,a/the/an --> 干掉蒜胖,mother --> mom,small --> little
一個分詞器抛蚤,很重要台谢,將一段文本進行各種處理,最后處理好的結果才會拿去建立倒排索引
(2)岁经、內(nèi)置分詞器的介紹
文本:Set the shape to semi-transparent by calling set_trans(5)
standard analyzer:set, the, shape, to, semi, transparent, by, calling, set_trans, 5(默認的是standard)
simple analyzer:set, the, shape, to, semi, transparent, by, calling, set, trans
whitespace analyzer:Set, the, shape, to, semi-transparent, by, calling, set_trans(5)
language analyzer(特定的語言的分詞器朋沮,比如說,english,英語分詞器):set, shape, semi, transpar, call, set_tran, 5
7樊拓、對第3點中的為什么做出解答
(1)纠亚、query string分詞
query string必須以和index建立時相同的analyzer進行分詞
query string對exact value和full text的區(qū)別對待:
date:exact value
_all:full text
比如我們有一個document,其中有一個field筋夏,包含的value是:hello you and me蒂胞,建立倒排索引
我們要搜索這個document對應的index,搜索文本是hell me条篷,這個搜索文本就是query string
query string骗随,默認情況下,es會使用它對應的field建立倒排索引時相同的分詞器去進行分詞赴叹,分詞和normalization鸿染,只有這樣,才能實現(xiàn)正確的搜索
知識點:不同類型的field乞巧,可能有的就是full text涨椒,有的就是exact value
post_date,date:exact value
_all:full text绽媒,分詞和normalization
(2)蚕冬、mapping引入案例遺留問題大揭秘
GET /_search?q=2017-01-01
這樣時,沒有指定字段些椒,query string會用跟建立倒排索引進行分詞播瞳,所以會查出來三條。
GET /_search?q=post_date:2017-01-01
post_date免糕,會作為exact value去建立索引赢乓,所以只有一條
GET /_search?q=post_date:2017
因為是es 5.2以后做的一個優(yōu)化,且為exact value去建立索引石窑,所以查的時候會給返回一條牌芋,后面有機會了解后做講解
(3)、測試分詞器松逊,用下面的方法可以看是怎么分詞的
GET /_analyze
{
??"analyzer": "standard",
??"text": "Text to analyze"
}
(3)躺屁、mapping數(shù)據(jù)類型
String/text
byte,short经宏,integer犀暑,long
float,double
boolean
date
自己映射時什么做相應處理
true or false --> boolean
123 --> long
123.45 --> double
2017-01-01 --> date
"hello world" --> string/text
8烁兰、總結
(1)往es里面直接插入數(shù)據(jù)耐亏,es會自動建立索引,同時建立type以及對應的mapping
(2)mapping中就自動定義了每個field的數(shù)據(jù)類型
(3)不同的數(shù)據(jù)類型(比如說text和date)沪斟,可能有的是exact value广辰,有的是full text
(4)exact value,在建立倒排索引的時候,分詞的時候择吊,是將整個值一起作為一個關鍵詞建立到倒排索引中(如post_date:2017-01-01)李根;full text,會經(jīng)歷各種各樣的處理几睛,分詞/normaliztion(時態(tài)轉換房轿,同義詞轉換,大小寫轉換)枉长,才會建立到倒排索引中
(5)同時呢冀续,exact value和full text類型的field就決定了,在一個搜索過來的時候必峰,對exact value field或者是full text field進行搜索的行為也是不一樣的洪唐,會跟建立倒排索引的行為保持一致;比如說exact value搜索的時候吼蚁,就是直接按照整個值進行匹配凭需,full text/query string,也會進行分詞和normalization再去倒排索引中去搜索
(6)可以用es的dynamic mapping肝匆,讓其自動建立mapping粒蜈,包括自動設置數(shù)據(jù)類型;也可以提前手動創(chuàng)建index和type的mapping旗国,自己對各個field進行設置枯怖,包括數(shù)據(jù)類型,包括索引行為能曾,包括分詞器度硝,等等
mapping,就是index的type的元數(shù)據(jù)寿冕,每個type都有一個自己的mapping蕊程,決定了數(shù)據(jù)類型,建立倒排索引的行為驼唱,還有進行搜索的行為
?
?
[if !supportLists]9藻茂、[endif]如何建立索引
analyzed分詞
not_analyzed//不分
no不能被搜索
[if !supportLists](1)[endif]、修改mapping
只能創(chuàng)建index時手動建立mapping玫恳,或者新增field mapping辨赐,但是不能update field mapping
PUT /website
{
??"mappings": {
????"article": {
??????"properties": {
????????"author_id": {
??????????"type": "long"
????????},
????????"title": {
??????????"type": "text",
??????????"analyzer": "english"
????????},
????????"content": {
??????????"type": "text"
????????},
????????"post_date": {
??????????"type": "date"
????????},
????????"publisher_id": {
??????????"type": "text",
??????????"index": "not_analyzed"
????????}
??????}
????}
??}
}
如果做修改會報錯
PUT /website
{
??"mappings": {
????"article": {
??????"properties": {
????????"author_id": {
??????????"type": "text"
????????}
??????}
????}
??}
}
報錯
{
??"error": {
????"root_cause": [
??????{
????????"type": "index_already_exists_exception",
????????"reason": "index [website/co1dgJ-uTYGBEEOOL8GsQQ] already exists",
????????"index_uuid": "co1dgJ-uTYGBEEOOL8GsQQ",
????????"index": "website"
??????}
????],
????"type": "index_already_exists_exception",
????"reason": "index [website/co1dgJ-uTYGBEEOOL8GsQQ] already exists",
????"index_uuid": "co1dgJ-uTYGBEEOOL8GsQQ",
????"index": "website"
??},
??"status": 400
}
新增一個字段時是可以的
PUT /website/_mapping/article
{
??"properties" : {
????"new_field" : {
??????"type" : ???"string",
??????"index": ???"not_analyzed"
????}
??}
}
[if !supportLists](2)[endif]測試建立好的mapping是怎么進行分詞的
GET /website/_analyze
{
??"field": "content",
??"text": "my-dogs"
}
[if !supportLists](3)[endif]特殊類型
{ "tags": [ "tag1", "tag2" ]}//多字段
null,[]京办,[null]//為null的
Object類型的
多種類型的掀序,es底層可能會對它做特殊處理
如:{
??"address": {
????"country": "china",
????"province": "guangdong",
????"city": "guangzhou"
??},
??"name": "jack",
??"age": 27,
??"join_date": "2017-01-01"
}
es處理后
{
????"name": ???????????[jack],
????"age": ?????????[27],
????"join_date": ?????[2017-01-01],
????"address.country": ????????[china],
????"address.province": ??[guangdong],
????"address.city": ?[guangzhou]
}
如:
{
????"authors": [
????????{ "age": 26, "name": "Jack White"},
????????{ "age": 55, "name": "Tom Jones"},
????????{ "age": 39, "name": "Kitty Smith"}
????]
}
ES處理后
{
????"authors.age": ???[26, 55, 39],
????"authors.name": ??[jack, white, tom, jones, kitty, smith]
}