烟台做网站打电话话术,公众号小程序怎么做,舆情分析网站,seo基础教程使用写在前面
本文看下es的nested嵌套对象相关内容。
1#xff1a;es用了啥范式#xff1f;
在关系型数据库中定义了6大数据库范式,即1#xff0c;2#xff0c;3#xff0c;BC#xff0c;4#xff0c;5的NF#xff08;normal form#xff09;,分别如下#xff1a;
1N…写在前面
本文看下es的nested嵌套对象相关内容。
1es用了啥范式
在关系型数据库中定义了6大数据库范式,即123BC45的NFnormal form,分别如下
1NF:每个列都不可拆分即都是原子的
2NF:在满足1NF的基础上消除部分函数依赖
3NF:在满足2NF的基础上消除传递函数依赖
BCNF:在满足3NF的基础上消除主属性对于码的部分函数依赖和传递函数依赖此时和非主键列没有关系
4NF在满足BCNF的基础上消除表内的多对多关系
5NF:略数据库范式的目的在于减少更新的复杂度以及降低磁盘的存储空间。其中对于第二个问题存储设备目前非常廉价而且容量很大所以不是什么问题了。对于第一个更新的复杂度问题会带来的查询效率变低的问题因为需要更多的关联join。那么对于es来说它是使用了哪种范式呢因为es的设计目标是快速查询,所以使用到是反范式即冗余存储。比如如下的数据 如果按照关系型数据库范式来设计user的信息需要存储到单独的一张表中去但是在es中就是在一个对象中来存储对于这种存储es支持非常方便和高效的查询
准备数据
DELETE blog
# 设置blog的 Mapping
PUT /blog
{mappings: {properties: {content: {type: text},time: {type: date},user: {properties: {city: {type: text},userid: {type: long},username: {type: keyword}}}}}
}# 插入一条 Blog 信息
PUT blog/_doc/1
{content:I like Elasticsearch,time:2019-01-01T00:00:00,user:{userid:1,username:Jack,city:Shanghai}
}查询
# 查询 Blog 信息
POST blog/_search
{query: {bool: {must: [{match: {content: Elasticsearch}},{match: {user.username: Jack}}]}}
}我们再来看一个存储对象数组的例子
准备数据
DELETE my_movies# 电影的Mapping信息
PUT my_movies
{mappings : {properties : {actors : {properties : {first_name : {type : keyword},last_name : {type : keyword}}},title : {type : text,fields : {keyword : {type : keyword,ignore_above : 256}}}}}
}# 写入一条电影信息
POST my_movies/_doc/1
{title:Speed,actors:[{first_name:Keanu,last_name:Reeves},{first_name:Dennis,last_name:Hopper}]
}查询first_name为Keanu并且last_name为Hopper的文档信息
POST my_movies/_search
{query: {bool: {must: [{match: {actors.first_name: Keanu}},{match: {actors.last_name: Hopper}}]}}}按照正常思维应该查不到才对但为什么查到了呢这和es的数据存储方式有关系对于数组es默认是按照一种扁平结构来存储的如下 这种存储结构的好处是可以加快查询的速度但坏处呢就是上例中反直觉结果。
所以如果能够让内部的对象也按照单独文档来存储就能解决这个查询错误的问题了而想要使用单独的文档来存储内部的对象就需要用到es提供的nested对象功能继续来看作为本文的主题必须单开一部分还必须是一级标题。
2nested对象
nested是一种定义对象的数据类型比如可通过如下方式来定义一个nested的类型: 在保存时会被保存为单独的文档查询时通过join的方式来查询当然此时会牺牲掉部分查询性能。
创建如下的mapping
DELETE my_movies
# 创建 Nested 对象 Mapping
PUT my_movies
{mappings : {properties : {actors : {type: nested,properties : {first_name : {type : keyword},last_name : {type : keyword}}},title : {type : text,fields : {keyword:{type:keyword,ignore_above:256}}}}}
}接着来插入测试数据
POST my_movies/_doc/1
{title:Speed,actors:[{first_name:Keanu,last_name:Reeves},{first_name:Dennis,last_name:Hopper}]
}此时存储结构为红框中所示
查询first_name为Keanu并且last_name为Hopper的文档信息 此时就查询不到了
POST my_movies/_search
{query: {bool: {must: [{nested: {path: actors,query: {bool: {must: [{match: {actors.first_name: Keanu}},{match: {actors.last_name: Hopper}}]}}}}]}}
}当然如果把actors.last_name: Hopper改为Reeves是能查出来数据的
写在后面
参考文章列表
关系型数据库MySQL及其优化 。