ElasticSearch中distinct、count和group by的实现

brew安装 elasticsearch
1、brew install elasticsearch
To have launchd start elasticsearch now and restart at login:
 	brew services start elasticsearch
Or, if you don't want/need a background service you can just run:
  elasticsearch
2、启动elasticsearch
	brew services start elasticsearch
	elasticsearch
3、访问:http://localhost:9200
安装elasticsearch-head插件
这个插件可以直观的看到ES运行和数据存储的情况。
1.  下载elasticsearch-head到本地的elasticsearchhead目录下,命令如下:
    git clone git://github.com/mobz/elasticsearch-head.git
2.  切换到刚刚的下载目录下
    cd ⁨⁨elasticsearch-head/
3. 安装elasticsearch-head的依赖
   npm install
4. 启动这个js插件 npm run start
5. 查看ES运行情况
   http://localhost:9100

因为在9100这个端口访问9200这个端口涉及到跨域问题,所以要先配置下ES的跨域允许设置问题

打开ES的配置文件( /Users/sunww/Documents/JAVA/elasticsearch-6.6.2/config/elasticsearch.yml),输入下面的两句
http.cors.enabled: true
http.cors.allow-origin: "*"
参考原文地址
https://www.jianshu.com/p/62bed9cc8349
https://www.cnblogs.com/Ace-suiyuan008/p/9958552.html
1 - distinct
SELECT DISTINCT(user_id) FROM table WHERE user_id_type = 3;
{
  "query": {
    "term": {
      "user_id_type": 3
    }
  },
  "collapse": {
    "field": "user_id"
  }
}
{
  ...
  "hits": {
    "hits": [
      {
        "_index": "es_qd_mkt_visitor_packet_dev_v1_20180621",
        "_type": "ad_crowd",
        "_source": {
          "user_id": "wx2af8414b502d4ca2_oHtrD0Vxv-_8c678figJNHmtaVQQ",
          "user_id_type": 3
        },
        "fields": {
          "user_id": [
            "wx2af8414b502d4ca2_oHtrD0Vxv-_8c678figJNHmtaVQQ"
          ]
        }
      }
    ]
  }
}

总结:使用collapse字段后,查询结果中[hits]中会出现[fields]字段,其中包含了去重后的user_id

2 - count + distinct
SELECT COUNT(DISTINCT(user_id)) FROM table WHERE user_id_type = 3;
{
  "query": {
    "term": {
      "user_id_type": 3
    }
  },
  "aggs": {
    "count": {
      "cardinality": {
        "field": "user_id"
      }
    }
  }
}
{
  ...
  "hits": {
  ...
  },
  "aggregations": {
    "count": {
      "value": 121
    }
  }
}

总结:aggs中cardinality的字段代表需要distinct的字段

3 - count + group by
SELECT COUNT(user_id) FROM table GROUP BY user_id_type;
{
  "aggs": {
    "user_type": {
      "terms": {
        "field": "user_id_type"
      }
    }
  }
}
{
  ...
  "hits": {
    ...
  },
  "aggregations": {
    "user_type": {
      ...
      "buckets": [
        {
          "key": 4,
          "doc_count": 1220
        },
        {
          "key": 3,
          "doc_count": 488
        }
      ]
    }
  }
}

总结:aggs中terms的字段代表需要gruop by的字段

4 - count + distinct + group by
SELECT COUNT(DISTINCT(user_id)) FROM table GROUP BY user_id_type;
{
  "aggs": {
    "user_type": {
      "terms": {
        "field": "user_id_type"
      },
      "aggs": {
        "count": {
          "cardinality": {
            "field": "user_id"
          }
        }
      }
    }
  }
}
{
  ...
  "hits": {
    ...
  },
  "aggregations": {
    "user_type": {
      ...
      "buckets": [
        {
          "key": 4,
          "doc_count": 1220, //去重前数据1220条
          "count": {
            "value": 276 //去重后数据276条
          }
        },
        {
          "key": 3,
          "doc_count": 488, //去重前数据488条
          "count": {
            "value": 121 //去重后数据121条
          }
        }
      ]
    }
  }
}
5 - count + distinct + group by + where
SELECT COUNT(DISTINCT(user_id)) FROM table WHERE user_id_type = 2 GROUP BY user_id;

总结:对于既有group by又有distinct的查询要求,需要在aggs中嵌套子aggs

6 - 注意事项

collapse关键字

1、折叠功能ES5.3版本之后才发布的。
2、聚合&折叠只能针对keyword类型有效;
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
您好!对于JavaElasticsearch(ES)库,您可以使用聚合(Aggregation)来实现类似SQLGROUP BY和COUNT操作。以下是一个示例代码: ```java import org.elasticsearch.action.search.SearchResponse; import org.elasticsearch.client.Client; import org.elasticsearch.index.query.QueryBuilders; import org.elasticsearch.search.aggregations.AggregationBuilders; import org.elasticsearch.search.aggregations.bucket.terms.StringTerms; import org.elasticsearch.search.aggregations.metrics.sum.Sum; import org.elasticsearch.search.sort.SortBuilders; import org.elasticsearch.search.sort.SortOrder; public class EsGroupByCountExample { public static void main(String[] args) { // 创建Elasticsearch客户端 Client client = createClient(); // 构建聚合查询 SearchResponse response = client.prepareSearch("your_index") .setQuery(QueryBuilders.matchAllQuery()) .addAggregation( AggregationBuilders.terms("group_by_field") .field("your_field") .order(SortOrder.DESC) .size(10) .subAggregation(AggregationBuilders.sum("count") .field("your_count_field")) ) .execute() .actionGet(); // 解析聚合结果 StringTerms terms = response.getAggregations().get("group_by_field"); for (StringTerms.Bucket bucket : terms.getBuckets()) { String key = bucket.getKeyAsString(); Sum sum = bucket.getAggregations().get("count"); double count = sum.getValue(); System.out.println(key + ": " + count); } // 关闭客户端连接 client.close(); } // 创建Elasticsearch客户端 private static Client createClient() { // 这里省略了创建Elasticsearch客户端的代码 // 您可以根据自己的需求选择合适的方式创建客户端 return null; } } ``` 请注意,上述代码的"your_index"、"your_field"和"your_count_field"需要替换为您实际使用的索引名称、字段名称和计数字段名称。 这段代码将执行一个聚合查询,按指定字段分组,并计算每个分组的计数。然后,通过遍历聚合结果的桶(buckets),获取每个分组的键(key)和对应的计数值(count)。 希望这可以帮助到您!如果有任何进一步的问题,请随时提问。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值