空搜索 ,返回集群索引中的所有文档
http://192.168.1.135:9200/_search/
查询结果中的hits部分,total表示检索出的记录总数,还包含着查询的前十条记录
增删改查,复合查询
### 一、条件查询
http://192.168.1.135:9200/score-statistics-2019.10/_search/
查询mac为11010030333247333400f47c1cd5c200,且statisticsTypeCode为1012的记录
{
"query": {
"bool": {
"must":
[
{
"match": { "statisticsTypeCode": "1012" }
},
{
"match":{"mac":"11010030333247333400f47c1cd5c200"}
}
]
}
}
}
############# term 子句,筛选满足其中一个条件的集合
GET score-statistics-2019.10/_search
{
"from":0,"size": 40,
"query": {
"bool": {
"must":
[
{
"match": {
"statisticsTypeCode": "1017"
}
},
{
"terms": {
"mac": [
"110100303136473730001f2ea408548f",
"test1"
]
}
}
]
}
}
}
##### compound query(复合查询)bool query、boosting query、constant_score query、dis_max query的区别
######### 1、bool query(多查询或复合查询的默认查询方式)
用于组合多个叶子或复合查询子句的默认查询,包含must, should, must_not, or filter 。must和should子句将它们的分数组合在一起 - 匹配子句越多越好 - 而must_not和filter子句在过滤器上下文中执行。
must:返回的文档必须满足must子句的条件,并且参与计算分值
filter:返回的文档必须满足filter子句的条件。不参与计算分值
must_not:返回的文档必须不满足must_not定义的条件。不参与评分。
should:返回的文档可能满足should子句的条件。在一个Bool查询中,如果没有must或者filter,有一个或者多个should子句,那么只要满足一个就可以返回。minimum_should_match参数定义了至少满足几个子句。
注1:评分计算
bool 查询会为每个文档计算相关度评分 _score , 再将所有匹配的 must 和 should 语句的分数 _score 求和,最后除以 must 和 should 语句的总数。
must_not 语句不会影响评分; 它的作用只是将不相关的文档排除。
注2:控制精度
所有 must 语句必须匹配,所有 must_not 语句都必须不匹配,但有多少 should 语句应该匹配呢? 默认情况下,没有 should 语句是必须匹配的,只有一个例外:那就是当没有 must 语句的时候,至少有一个 should 语句必须匹配。
就像我们能控制 match 查询的精度 一样,我们可以通过 minimum_should_match 参数控制需要匹配的 should 语句的数量, 它既可以是一个绝对的数字,又可以是个百分比:
######### 2、boosting query
提升查询可用于有效降级与给定查询匹配的结果。与bool查询中的“NOT”子句不同,这仍然会选择包含不良术语的文档,但会降低其总分。
######### 3、constant_score query
含另一个查询但在过滤器上下文中执行的查询。所有匹配的文档都给出相同的“常量”_score
######### 4、dis_max query
一个接受多个查询的查询,并返回与任何查询子句匹配的任何文档。虽然bool查询组合了所有匹配查询的分数,但dis_max查询使用单个最佳匹配查询子句的分数。
一个查询,它生成由其子查询生成的文档的并集,并为每个文档评分由任何子查询生成的该文档的最大分数,以及任何其他匹配子查询的平局增量。
当在具有不同增强因子的多个字段中搜索单词时,这非常有用(因此不能将字段等效地组合到单个搜索字段中)。我们希望主要分数是与最高提升相关联的分数,而不是字段分数的总和(如布尔查询所给出的)。如果查询是“albino elephant”,则这确保匹配一个字段的“albino”和匹配另一个的“elephant”获得比匹配两个字段的“albino”更高的分数。要获得此结果,请同时使用Boolean Query和DisjunctionMax Query:对于每个术语,DisjunctionMaxQuery在每个字段中搜索它,而将这些DisjunctionMaxQuery的集合组合成BooleanQuery。
######### 5、function_score query
使用函数修改主查询返回的分数,以考虑流行度、最近度、距离或使用脚本实现的自定义算法等因素。
### 二、分页查询 ( "from":0,"size": 40 )
GET score-statistics-2019.10/_search
{
"from":10,"size": 40,
"query": {
"bool": {
"should":
[
{
"match": { "statisticsTypeCode": "1012" }
},
{
"match":{"mac":"110100303136473730001f2ea408548f"}
}
]
}
}
}
### 三、,count计数
GET score-statistics-2019.10/_count
{
"query": {
"bool": {
"must":
[
{
"match": {
"statisticsTypeCode": "1017"
}
},
{
"terms": {
"mac": [
"110100303136473730001f2ea408548f",
"test1"
]
}
}
]
}
}
}
聚合查询,值运算
https://www.cnblogs.com/pilihaotian/p/5845754.html
单值聚合 sum avg min max,Cardinality (求基数)
{
"size": 0,
"aggs": {
"return_balance": {
"sum": {
"field": "balance"
}
}
}
}
返回balance之和,其中size=0 表示不需要返回参与查询的文档
多值聚合
percentiles 求百分比
{
"size": 0,
"aggs": {
"states": {
"terms": {
"field": "gender"
},
"aggs": {
"banlances": {
"percentile_ranks": {
"field": "balance",
"values": [
20000,
]
}
}
}
}
}
status统计
查看balance的统计情况:
{
"size": 0,
"aggs": {
"balance_stats": {
"stats": {
"field": "balance"
}
}
}
}
extended_stats 扩展统计
{
"size": 0,
"aggs": {
"balance_stats": {
"extended_stats": {
"field": "balance"
}
}
}
}
### 高级索引语法 高级检索语法:term, wildcard, prefix, fuzzy, range, query_string, text, missing
term:严格匹配条件,所查询的字段内容要与填入查询框搜索值一致;
wildcard:通配符查询,* 表示全匹配,? 表示单一匹配,etc: aaa* 或者 a?b;
prefix:前缀匹配,搜索框如果输入aa,那么可能匹配到的字段值为 aab,aavb等;
fuzzy min_similarity:弹性模糊匹配,有两个搜索框,第一个搜索框为搜索匹配值,会自动纠错,比如输入 ggjk,那么可能会匹配到ggjo,第二个框为最小相似度,采用的算法是Damerau-Levenshtein(最佳字符串对齐)算法,不建议填写这个框,我到发稿前也是被搞的头皮发麻,等我完全吃透再更新;
fuzzy max_expansions :弹性模糊匹配,有两个搜索框,第一个搜索框为搜索匹配值,会自动纠错,比如输入gjk,那么可能会匹配到ggjo,第二个框是最大扩展匹配数,比如是1,那么ggjk只会随机模糊匹配到一种可能结果,即使它会出现2种或者更加多,也只会搜索一种;
range:范围查询,gt为大于,gte为大于等于,lt小于,lte小于等于,所搜索的字段值在两个搜索框标识数值之间;
query_string:字符片段查询,如果是数字,则严格匹配数字,如果是字符串,则按照自身或者分片词匹配;
text:分片词查询,等确定后更新;
missing:查询没有定义该字段或者该字段值为null的数据。
####### Range Query
查询符合must条件而且timestamp在1571969062到1571969065之间的结果
GET score-statistics-2019.10/_search
{
"from":0,"size": 40,
"query": {
"bool": {
"must":
[
{
"match": {
"statisticsTypeCode": "1017"
}
},
{
"terms": {
"mac": [
"110100303136473730001f2ea408548f",
"test1"
]
}
}
],
"filter": {
"range": {
"timestamp": {
"gte": 1571969062,
"lte": 1571969065
}
}
}
}
}
}
gte: 大于或等于
gt: 大于
lte: 小于或等于
lt: 小于
boost: 设置查询的提升值,默认为1.0 (修改得分)
######### Elasticsearch排序 根据时间戳排序
https://www.elastic.co/guide/cn/elasticsearch/guide/current/_Sorting.html#_Sorting_on_Multivalue_Fields
ES中排序的分类
根据建模方法的不同,ES中排序分为以下几种,每种都有不同的排序写法和局限:
嵌套文档-根据主文档字段排序
嵌套文档-根据内嵌文档字段排序
父子文档-查父文档-根据子文档排序
父子文档-查子文档-根据父文档排序
更复杂的情况,父子文档里又嵌套了文档,然后进行排序
更更复杂情况,父子文档里又嵌套了文档,然后进行脚本字段排序
更更更复杂情况,父子文档里又嵌套了文档,然后使用自定义脚本进行评分排序……
###按照字段的值排序编辑
根据timestamp降序排序,这种排序不会不计算得分("_score" : null,),因为score并没有用于排序
GET score-statistics-2019.10/_search
{
"from":0,"size": 40,
"query": {
"bool": {
"must":
[
{
"match": {
"statisticsTypeCode": "1017"
}
},
{
"terms": {
"mac": [
"110100303136473730001f2ea408548f",
"test1"
]
}
}
]
}
}
, "sort": [
{
"timestamp": {
"order": "desc"
}
}
]
}
多级排序
假定我们想要结合使用 date 和 _score 进行查询,并且匹配的结果首先按照日期排序,然后按照相关性排序:
GET /_search
{
"query" : {
"bool" : {
"must": { "match": { "tweet": "manage text search" }},
"filter" : { "term" : { "user_id" : 2 }}
}
},
"sort": [
{ "date": { "order": "desc" }},
{ "_score": { "order": "desc" }}
]
}
多值字段排序
多值字段的排序编辑
一种情形是字段有多个值的排序, 需要记住这些值并没有固有的顺序;一个多值的字段仅仅是多个值的包装,这时应该选择哪个进行排序呢?
对于数字或日期,你可以将多值字段减为单值,这可以通过使用 min 、 max 、 avg 或是 sum 排序模式 。 例如你可以按照每个 date 字段中的最早日期进行排序,通过以下方法:
"sort": {
"dates": {
"order": "asc",
"mode": "min"
}
}
#### 查询记录数 GET score-statistics-2019.10/_count这个api来查询
GET score-statistics-2019.10/_count
{
"query": {
"bool": {
"must":
[
{
"match": {
"statisticsTypeCode": "1017"
}
},
{
"terms": {
"mac": [
"110100303136473730001f2ea408548f",
"test1"
]
}
}
]
}
}
}
复合查询的java实现
public List queryByTagLogs(String logType, Map<String, Object> contextMap, Date startTime, Date endTime) {
List list = new ArrayList();
// 1.创建并设置SearchSourceBuilder对象
SearchSourceBuilder sourceBuilder = new SearchSourceBuilder();
BoolQueryBuilder boolQueryBuilder = QueryBuilders.boolQuery();
boolQueryBuilder.must(QueryBuilders.matchAllQuery());//查询所有 此处为匹配所有文档
//elasticsearch 里默认的IK分词器是会将每一个中文都进行了分词的切割,所以你直接想查一整个词 加上.keyword
boolQueryBuilder.must(QueryBuilders.termQuery("logType.keyword", logType));
//时间范围的设定
if (startTime != null && endTime != null){
boolQueryBuilder.must(QueryBuilders.rangeQuery("operateAt").from(startTime)
.to(endTime));
}
//把其它参数加进去
if (contextMap != null){
contextMap.forEach((key, value) -> {S
if (value != null && !"".equals(value)) {
boolQueryBuilder.must(QueryBuilders.matchPhraseQuery(key, value));//must相当于and
}
});
}
sourceBuilder.query(boolQueryBuilder);// 查询条件--->生成DSL查询语句
sourceBuilder.from(0);// 第几页
sourceBuilder.size(100);// 每页多少条数据
// sourceBuilder.sort("id", SortOrder.ASC); // 设置排序规则
// sourceBuilder.timeout(new TimeValue(2000));// 设置超时时间为2s
// 2.创建并设置SearchRequest对象
SearchRequest searchRequest = new SearchRequest(INDEX);
searchRequest.types(TYPE); // 设置request要搜索的索引和类型
searchRequest.source(sourceBuilder);// 设置SearchSourceBuilder查询属性
try {
SearchResponse search = client.search(searchRequest, RequestOptions.DEFAULT);//查询
SearchHits hits = search.getHits();
for (SearchHit hit: hits
) {
Map<String, Object> sourceAsMap = hit.getSourceAsMap();
String operateAt = sourceAsMap.get("operateAt").toString();
SimpleDateFormat formatter = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS");
long time = formatter.parse(operateAt).getTime();
sourceAsMap.put("operateAt", time);
list.add(sourceAsMap);
}
} catch (IOException e) {
log.error(e.getMessage(), e);
} catch (ParseException e) {
log.error(e.getMessage(), e);
}
return list;
}
public Object queryAdsOperateTime(String mac, Long startTimeStamp, Long endTimeStamp,Integer pageSize,Integer pageNum) throws IOException {
SearchSourceBuilder searchSourceBuilder=new SearchSourceBuilder();
BoolQueryBuilder boolQueryBuilder= QueryBuilders.boolQuery();
boolQueryBuilder.must(QueryBuilders.matchQuery("statisticsTypeCode",CAR_ADS_EJECT.getStatisticsTypeCode()));
if (StringUtil.isNotEmpty(mac)){
boolQueryBuilder.must(QueryBuilders.matchQuery("mac",mac));
}
if (startTimeStamp!=0&&endTimeStamp!=0){
boolQueryBuilder.must(QueryBuilders.rangeQuery("timestamp").from(startTimeStamp).to(endTimeStamp));
}
searchSourceBuilder.query(boolQueryBuilder);
searchSourceBuilder.from((pageNum-1)*pageSize);
searchSourceBuilder.size(pageSize);
CountRequest countRequest=new CountRequest();
countRequest.source(searchSourceBuilder);
CountResponse countResponse=esFactory.getClient().count(countRequest,RequestOptions.DEFAULT);
long ejecj=countResponse.getCount();
long click=1;
long close=1;
/* esFactory.getClient().search();*/
Map resultMap=new HashMap();
resultMap.put("ejecj",ejecj);
resultMap.put("click",click);
resultMap.put("close",close);
return new R<>(resultMap,"统计浮窗操作的次数,弹出、点击、关闭");
}
public Object queryAdsOperateTime(String mac, Long startTimeStamp, Long endTimeStamp) throws IOException {
SearchSourceBuilder searchSourceBuilder=new SearchSourceBuilder();
BoolQueryBuilder boolQueryBuilder= QueryBuilders.boolQuery();
boolQueryBuilder.must(QueryBuilders.matchQuery("statisticsTypeCode",CAR_ADS_EJECT.getStatisticsTypeCode()));
if (StringUtil.isNotEmpty(mac)){
boolQueryBuilder.must(QueryBuilders.matchQuery("mac",mac));
}
if (startTimeStamp!=0&&endTimeStamp!=0){
boolQueryBuilder.must(QueryBuilders.rangeQuery("timestamp").from(startTimeStamp).to(endTimeStamp));
}
searchSourceBuilder.query(boolQueryBuilder);
CountRequest countRequest=new CountRequest();
countRequest.source(searchSourceBuilder);
CountResponse countResponse=esFactory.getClient().count(countRequest,RequestOptions.DEFAULT);
long ejecj=countResponse.getCount();
long click=1;
long close=1;
/* esFactory.getClient().search();*/
Map resultMap=new HashMap();
resultMap.put("ejecj",ejecj);
resultMap.put("click",click);
resultMap.put("close",close);
return new R<>(resultMap,"统计浮窗操作的次数,弹出、点击、关闭");
}