顿搜
07. ES字段类型介绍与设置方式——ElasticSearch基础专栏
一、常用类型
1.1 binary
表示可以存储编码为Base64的字符串或者二进制值。
1.2 boolean
表示可以存储true和false的布尔值。
在使用布尔类型字段时需要注意的是,布尔类型的查询不能使用0或者1替代,否则会抛出异常
如果需要对布尔值进行转换,可以使用“运行时”脚本来处理
GET myindex/_search
{
"fields": [
{"field": "weight"}
],
"runtime_mappings": {
"weight": {
"type": "long",
"script": "emit(doc['is_published'].value ? 1: 0)" // 使用"运行时"脚本转换布尔值
}
}
}返回值
{
"_index":"myindex",
"_type":"_doc",
"_id":"1",
"_score":1,
"_source":{
"is_published":"true"
},
"fields":{
"weight":[
1 // 布尔值被“运行时”脚本转换为对应的值
]
}
}1.3 keyword
该字段类型的数据在存储时不会进行分词处理,适合进行统计分析,不能进行全文搜索。
此类型的字段通常用于排序、聚合查询等
GET myindex-2_11/_doc/_search?q=tag:北京 // 查询索引库中tag字段是"北京"且完全匹配的内容1.4 numbers
用于表示数字类型,包含
- byte: 8位 [$-2^{7}, 2^{7}-1$]
- short: 16位 [$-2^{15}, 2^{15}-1$]
- integer: 32位 [$-2^{31}, 2^{31}-1$]
- long: 64位 [$-2^{63}, 2^{63}-1$]
- float: [$2^{-149}, (2-2^{-23})*2^{127}$]
- double: [$2^{-1074}, (2-2^{-52})*2^{1023}$]
- half_float: [$2^{-24}$, 65504]
- unsigned_long: [0, $2^{64}-1$]
PUT myindex
{
"mappings": {
"properties": {
"number": {
"type": "integer"
},
"time_in_seconds": {
"type": "float"
},
"price": {
"type": "scaled_float",
"scaling_factor": 100
}
}
}
}
- "scaling_factor"参数表示数值在存储时使用了缩放因子,该值在存储时乘以缩放因子并四舍五入到最接近long类型的值
- 比如1.11实际存储的数据是111
1.5 date
表示可以存储日期类型的数据。
PUT myindex
{
"mappings": {
"properties": {
"date": {
"type": "date",
"format":"yyyy-MM-dd HH:mm:ss"
}
}
}
}1.6 alias
表示为现有字段定义别名。
PUT myindex
{
"mappings": {
"properties": {
"age": {
"type": "long"
},
"aliasage": {
"type": "alias", // 别名类型
"path": "age"
}
}
}
}在使用别名时需要注意的是,可以使用别名进行数据的搜索,但是不能使用别名进行数据的写入
1.7 text
该字段类型的数据在存储时会进行分词并建立索引,适合进行全文搜索,不能进行统计分析。
text类型的字段不适合进行排序,也不适合进行聚合计算
text查询一般使用match, keyword既可以使用match、也可以使用term
要对文本字段执行更多操作,可以使用多字段映射,其中既有text类型可以用于全文搜索,又有keyword类型可以用于聚合分析
PUT myindex
{
"mappings": {
"properties": {
"my_field": {
"type": "text",
"fields": {
"keyword": {
"type": "keyword"
}
}
}
}
}
}二、对象和关系类型
2.1 object
实际就是JSON数据格式, 表示一个JSON对象。
PUT myindex
{
"mappings": {
"properties": {
"manager": {
"properties": {
"age": { "type": "integer" },
"name": {
"properties": {
"first": { "type": "text" },
"last": { "type": "text" }
}
}
}
}
}
}
}- 使用嵌套的JSON数据格式进行写入
PUT myindex/_doc/1
{
"manager": {
"age": 30,
"name": {
"first": "clay",
"last": "zhagng"
}
}
}- 使用简单的JSON数据格式进行写入
PUT myindex/_doc/2
{
"region": "US",
"manager.age": 30,
"manager.name.first": "John",
"manager.name.last": "Smith"
}使用以上两种方式写入数据不会影响数据的存储,但是会影响查询返回的结果是否打平展示
2.2 nested
嵌套类型,对象中可以嵌套对象。
nested(嵌套)类型是object数据类型的特殊版本,可以在对象中嵌套对象或在字段中存储键值对(Key-Value Pair)
PUT myindex
{
"mappings": {
"properties": {
"user": {
"type": "nested"
}
}
}
}
PUT myindex/_doc/1
{
"group" : "fans",
"user" : [ // 在索引库中插入文档数据,user字段中嵌套了键值对
{
"first" : "John",
"last" : "Smith"
},
{
"first" : "Alice",
"last" : "White"
}
]
}2.3 array
在Elasticsearch中,数组不需要专用的字段类型。
默认情况下,任何字段都可以包含0个或多个值,但是数组中的所有值必须具有相同的字段类型。
三、其余类型
3.1 range
表示范围类型。
PUT myindex
{
"mappings": {
"properties": {
"expected_attendees": {
"type": "integer_range"
},
"time_frame": {
"type": "date_range",
"format": "yyyy-MM-dd HH:mm:ss||yyyy-MM-dd||epoch_millis"
}
}
}
}
PUT myindex/_doc/1?refresh // 插入文档数据
{
"expected_attendees" : {
"gte" : 10,
"lt" : 20
},
"time_frame" : {
"gte" : "2021-10-31 12:00:00",
"lte" : "2021-11-01"
}
}
GET myindex/_search // 查询满足expected_attendees字段中数据范围内包括12的文档数据
{
"query" : {
"term" : {
"expected_attendees" : {
"value": 12
}
}
}
}3.2 rank_feature
表示排名类型。
rank_feature(排名)类型的字段可以存储数字,并且对搜索文档的分数有所影响
PUT myindex
{
"mappings": {
"properties": {
"pagerank": {
"type": "rank_feature"
},
"url_length": {
"type": "rank_feature",
"positive_score_impact": false
},
"topics": {
"type": "rank_features"
}
}
}
}查询索引库的content字段值中包含"2016"的文档,并根据评分(score字段的值)排序输出
GET myindex/_search
{
"query": {
"bool": {
"must": [
{
"match": {
"content": "2016"
}
}
],
"should": [
{
"rank_feature": {
"field": "pagerank"
}
},
{
"rank_feature": {
"field": "url_length",
"boost": 0.1
}
},
{
"rank_feature": {
"field": "topics.sports",
"boost": 0.4
}
}
]
}
}
}rank feature字段类型和rank features字段类型只能搭配rank_feature参数进行查询。
3.3 token_count
表示令牌计数类型
token_count(令牌计数)类型的字段实际上是一个integer类型字段,它可以对内容进行分词分析,存储内容被分词的数量
PUT myindex
{
"mappings": {
"properties": {
"name": {
"type": "text",
"fields": {
"length": {
"type": "token_count",
"analyzer": "standard"
}
}
}
}
}
}查询索引库中name字段被分词后,分词的数量等于2的文档
GET myindex/_search
{
"query": {
"term": {
"name.length":2
}
}
}使用分析语句对查询的内容进行预判分析
GET myindex/_analyze
{
"analyzer": "standard",
"text": ["John Smith"]
}响应结果
{
"tokens" : [
{
"token" : "john",
"start_offset" : 0, //起始偏移量
"end_offset" : 4, //结束偏移量
"type" : "<ALPHANUM>",
"position" : 0
},
{
"token" : "smith",
"start_offset" : 5, //起始偏移量
"end_offset" : 10, //结束偏移量
"type" : "<ALPHANUM>",
"position" : 1
}
]
}3.4 ip
用于IP地址的存储和查询的类型, 可以用于存储IPv4或IPv6地址
ip类型也支持IP地址的范围查询
查询IP地址符合"192.168.1.0/16"范围的文档数据
GET myindex-ip/_search
{
"query": {
"term": {
"ip_addr": "192.168.1.0/16"
}
}
}3.5 geo_point
地理点查询,即经纬度查询
PUT /myindex
{
"mappings": {
"hotels" : {
"properties": {
"pin" : {
"properties": {
"location" : {
"type" : "geo_point"
}
}
}
}
}
}
}插入酒店相关数据
PUT /myindex/1
{
"name": "XX大酒店",
"pin" : {
"location" : {
"lat" : 40.12, // 经度
"lon" : -71.34 // 纬度
}
}
}搜索指定的两个地理位置形成的矩形范围中包含的酒店信息
GET /myindex/_search
{
"query": {
"bool": {
"must": [
{"match_all": {}}
],
"filter": {
"geo_bounding_box": {
"pin.location": {
"top_left" : {
"lat" : 40.73,
"lon" : -74.1
},
"bottom_right" : {
"lat" : 40.01,
"lon" : -71.12
}
}
}
}
}
}
}搜索指定的多个地理位置形成的多边形范围中包含的酒店信息
GET /myindex/_search
{
"query": {
"bool": {
"must": [
{"match_all": {}}
],
"filter": {
"geo_polygon": {
"pin.location": {
"points": [
{"lat" : 40.73, "lon" : -74.1},
{"lat" : 40.01, "lon" : -71.12},
{"lat" : 50.56, "lon" : -90.58}
]
}
}
}
}
}
}搜索指定位置1000km范围内的酒店数据
GET /myindex/_search
{
"query": {
"bool": {
"must": [
{"match_all": {}}
],
"filter": {
"geo_distance": {
"distance": "1000km",
"pin.location": {
"lat": 40,
"lon": -74
}
}
}
}
}
}搜索距离指定位置一定范围内有多少个酒店
GET /myindex/_search
{
"size": 0,
"aggs": {
"count_by_distinct": {
"geo_distance": {
"field": "pin.location",
"origin": { // 指定的位置
"lat": 40,
"lon": 70
},
"ranges": [ // 范围控制
{"to" : 100},
{
"from": 100,
"to": 300
},
{"from": 300}
],
"unit": "mi", // 范围使用单位
"distance_type": "arc"
}
}
}
}3.6 geo_shape
地理形状查询,支持点、线、圈、多边形查询等, 比如我们想要找到最接近给定位置的路线,就可以使用此类型
PUT /myindex
{
"mappings": {
"properties": {
"location": {
"type": "geo_shape"
}
}
}
}插入地点相关信息
POST /myindex/_doc?refresh
{
"location": {
"type": "point",
"coordinates": [ 13.400544, 52.530286 ]
}
}搜索指定的两个位置范围内的地点
GET /myindex/_search
{
"query": {
"bool": {
"must": {
"match_all": {}
},
"filter": {
"geo_shape": {
"location": {
"shape": {
"type": "envelope",
"coordinates": [ [ 13.0, 53.0 ], [ 14.0, 52.0 ] ]
},
"relation": "within"
}
}
}
}
}
}3.7 search-as-you-type
search_as_you_type字段类型和text字段类型很相似,Elasticsearch对其进行了优化,为用户提供了开箱即用的功能。
search_as_you_type字段类型的字段可以创建一系列的子字段
PUT myindex{
"mappings": {
"properties": {
"my_field": {
"type": "search_as_you_type"
}
}
}
}当执行上面的映射模板时,将会为my_field字段创建以下所有字段作为其子字段。
- my_field
- my_field._2gram
- my_field._3gram
- my_field._index_pref
从my_field、my_field._2gram、my_field._3gram字段中筛选,返回内容中包含字符串"brown f"的文档数据
GET myindex/_search
{
"query": {
"multi_match": {
"query": "brown f",
"type": "bool_prefix",
"fields": [
"my_field",
"my_field._2gram",
"my_field._3gram"
]
}
}
}