通過統計彙總介面可以實現求最小值、求最大值、求和、求平均值、統計行數、去重統計行數、按欄位值分組、按範圍分組、按地理位置分組、按過濾條件分組、長條圖統計、日期長條圖統計、嵌套功能;同時支援多個統計彙總功能組合使用,滿足複雜的查詢需求。
背景資訊
統計彙總的詳細功能請參見下表。
功能 | 說明 |
最小值 | 返回一個欄位中的最小值,類似於SQL中的min。 |
最大值 | 返回一個欄位中的最大值,類似於SQL中的max。 |
和 | 返回數值欄位的總數,類似於SQL中的sum。 |
平均值 | 返回數值欄位的平均值,類似於SQL中的avg。 |
統計行數 | 返回指定欄位值的數量或者多元索引資料總行數,類似於SQL中的count。 |
去重統計行數 | 返回指定欄位不同值的數量,類似於SQL中的count(distinct)。 |
欄位值分組 | 根據一個欄位的值對查詢結果進行分組,相同的欄位值放到同一分組內,返回每個分組的值和該值對應的個數。 說明 當分組較大時,按欄位值分組可能會存在誤差。 |
多欄位分組 | 根據多個欄位對查詢結果進行分組,支援使用token進行翻頁。 |
範圍分組 | 根據一個欄位的範圍對查詢結果進行分組,欄位值在某範圍內放到同一分組內,返回每個範圍中相應的item個數。 |
地理位置分組 | 根據距離某一個中心點的範圍對查詢結果進行分組,距離差值在某範圍內放到同一分組內,返回每個範圍中相應的item個數。 |
過濾條件分組 | 按照過濾條件對查詢結果進行分組,擷取每個過濾條件匹配到的數量,返回結果的順序和添加過濾條件的順序一致。 |
長條圖統計 | 按照指定資料間隔對查詢結果進行分組,欄位值在相同範圍內放到同一分組內,返回每個分組的值和該值對應的個數。 |
日期長條圖統計 | 對日期欄位類型的資料按照指定間隔對查詢結果進行分組,欄位值在相同範圍內放到同一分組內,返回每個分組的值和該值對應的個數。 |
嵌套 | 分組類型的統計彙總功能支援嵌套,其內部可以添加子統計彙總。 |
多個統計彙總 | 多個統計彙總功能可以組合使用。 說明 當多個統計彙總的複雜度較高時可能會影響響應速度。 |
前提條件
已初始化Client。具體操作,請參見初始化OTSClient。
已在資料表上建立多元索引。具體操作,請參見建立多元索引。
最小值
返回一個欄位中的最小值,類似於SQL中的min。
參數
參數
說明
Name
自訂的統計彙總名稱,用於區分不同的統計彙總,可根據此名稱擷取本次統計彙總結果。
FieldName
用於統計彙總的欄位,僅支援Long、Double和Date類型。
Missing
當某行資料中的欄位為空白時,欄位值的預設值。
如果未設定Missing值,則在統計彙總時會忽略該行。
如果設定了Missing值,則使用Missing值作為欄位值的預設值參與統計彙總。
樣本
/** * 商品庫中有每一種商品的價格,求產地為浙江省的商品中,價格最低的商品價格是多少。 * 等效的SQL語句是SELECT min(column_price) FROM product where place_of_production="浙江省"; */ func min(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.TermQuery{"place_of_production", "浙江省"}). SetLimit(0). //如果只關心統計彙總結果,不關心具體資料,您可以將limit設定為0來提高效能。 Aggregation(search.NewMinAggregation("min_agg_1", "column_price").Missing(0.00))) searchResponse, err := client.Search(searchRequest) //執行查詢。 aggResults := searchResponse.AggregationResults //擷取統計彙總結果。 agg1, err := aggResults.Min("min_agg_1") //擷取名稱為"min_agg_1"的統計彙總結果。 if err != nil { panic(err) } if agg1.HasValue() { //名稱為"min_agg_1"的統計彙總結果是否有Value值。 fmt.Println(agg1.Value) //列印統計彙總結果。 } }
最大值
返回一個欄位中的最大值,類似於SQL中的max。
參數
參數
說明
Name
自訂的統計彙總名稱,用於區分不同的統計彙總,可根據此名稱擷取本次統計彙總結果。
FieldName
用於統計彙總的欄位,僅支援Long、Double和Date類型。
Missing
當某行資料中的欄位為空白時,欄位值的預設值。
如果未設定Missing值,則在統計彙總時會忽略該行。
如果設定了Missing值,則使用Missing值作為欄位值的預設值參與統計彙總。
樣本
/** * 商品庫中有每一種商品的價格,求產地為浙江省的商品中,價格最高的商品價格是多少。 * 等效的SQL語句是SELECT max(column_price) FROM product where place_of_production="浙江省"。 */ func max(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.TermQuery{"place_of_production", "浙江省"}). SetLimit(0). //如果只關心統計彙總結果,不關心具體資料,您可以將limit設定為0來提高效能。 Aggregation(search.NewMaxAggregation("max_agg_1", "column_price").Missing(0.00))) searchResponse, err := client.Search(searchRequest) //執行查詢。 aggResults := searchResponse.AggregationResults //擷取統計彙總結果。 agg1, err := aggResults.Max("max_agg_1") //擷取名稱為"max_agg_1"的統計彙總結果。 if err != nil { panic(err) } if agg1.HasValue() { //名稱為"max_agg_1"的統計彙總結果是否有Value值。 fmt.Println(agg1.Value) //列印統計彙總結果。 } }
和
返回數值欄位的總數,類似於SQL中的sum。
參數
參數
說明
Name
自訂的統計彙總名稱,用於區分不同的統計彙總,可根據此名稱擷取本次統計彙總結果。
FieldName
用於統計彙總的欄位,僅支援Long和Double類型。
Missing
當某行資料中的欄位為空白時,欄位值的預設值。
如果未設定Missing值,則在統計彙總時會忽略該行。
如果設定了Missing值,則使用Missing值作為欄位值的預設值參與統計彙總。
樣本
/** * 商品庫中有每一種商品的售出數量,求產地為浙江省的商品中,一共售出了多少件商品。如果某一件商品沒有該值,預設售出了10件。 * 等效的SQL語句是SELECT sum(column_price) FROM product where place_of_production="浙江省"。 */ func sum(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.TermQuery{"place_of_production", "浙江省"}). SetLimit(0). //如果只關心統計彙總結果,不關心具體資料,您可以將limit設定為0來提高效能。 Aggregation(search.NewSumAggregation("sum_agg_1", "column_price").Missing(0.00))) searchResponse, err := client.Search(searchRequest) //執行查詢。 aggResults := searchResponse.AggregationResults //擷取統計彙總結果。 agg1, err := aggResults.Sum("sum_agg_1") //擷取名稱為"sum_agg_1"的統計彙總結果。 if err != nil { panic(err) } fmt.Println(agg1.Value) //列印統計彙總結果。 }
平均值
返回數值欄位的平均值,類似於SQL中的avg。
參數
參數
說明
Name
自訂的統計彙總名稱,用於區分不同的統計彙總,可根據此名稱擷取本次統計彙總結果。
FieldName
用於統計彙總的欄位,僅支援Long、Double和Date類型。
Missing
當某行資料中的欄位為空白時,欄位值的預設值。
如果未設定Missing值,則在統計彙總時會忽略該行。
如果設定了Missing值,則使用Missing值作為欄位值的預設值參與統計彙總。
樣本
/** * 商品庫中有每一種商品的售出數量,求產地為浙江省的商品中,平均價格是多少。 * 等效的SQL語句是SELECT avg(column_price) FROM product where place_of_production="浙江省"。 */ func avg(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.TermQuery{"place_of_production", "浙江省"}). SetLimit(0). //如果只關心統計彙總結果,不關心具體資料,您可以將limit設定為0來提高效能。 Aggregation(search.NewAvgAggregation("avg_agg_1", "column_price").Missing(0.00))) searchResponse, err := client.Search(searchRequest) //執行查詢。 aggResults := searchResponse.AggregationResults //擷取統計彙總結果。 agg1, err := aggResults.Avg("avg_agg_1") //擷取名稱為"avg_agg_1"的統計彙總結果。 if err != nil { panic(err) } if agg1.HasValue() { //名稱為"agg1"的統計彙總結果是否有Value值。 fmt.Println(agg1.Value) //列印統計彙總結果。 } }
統計行數
返回指定欄位值的數量或者多元索引資料總行數,類似於SQL中的count。
通過如下方式可以統計多元索引資料總行數或者某個query匹配的行數。
使用統計彙總的count功能,在請求中設定count(*)。
使用query功能的匹配行數,在query中設定setGetTotalCount(true);如果需要統計多元索引資料總行數,則使用MatchAllQuery。
如果需要擷取多元索引資料某列出現的次數,則使用count(列名),可應用於稀疏列的情境。
參數
參數
說明
Name
自訂的統計彙總名稱,用於區分不同的統計彙總,可根據此名稱擷取本次統計彙總結果。
FieldName
用於統計彙總的欄位,僅支援Long、Double、Boolean、Keyword、Geo_point和Date類型。
樣本
/** * 商家庫中有每一種商家的懲罰記錄,求浙江省的商家中,有懲罰記錄的一共有多少個商家。如果商家沒有懲罰記錄,則商家資訊中不存在該欄位。 * 等效的SQL語句是SELECT count(column_history) FROM product where place_of_production="浙江省"。 */ func count(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.TermQuery{"place_of_production", "浙江省"}). SetLimit(0). //如果只關心統計彙總結果,不關心具體資料,您可以將limit設定為0來提高效能。 Aggregation(search.NewCountAggregation("count_agg_1", "column_price"))) searchResponse, err := client.Search(searchRequest) //執行查詢。 aggResults := searchResponse.AggregationResults //擷取統計彙總結果。 agg1, err := aggResults.Count("count_agg_1") //擷取名稱為"count_agg_1"的統計彙總結果。 if err != nil { panic(err) } fmt.Println(agg1.Value) //列印統計彙總結果。 }
去重統計行數
返回指定欄位不同值的數量,類似於SQL中的count(distinct)。
去重統計行數的計算結果是個近似值。
當去重統計行數小於1萬時,計算結果接近精確值。
當去重統計行數達到1億時,計算結果的誤差為2%左右。
參數
參數
說明
Name
自訂的統計彙總名稱,用於區分不同的統計彙總,可根據此名稱擷取本次統計彙總結果。
FieldName
用於統計彙總的欄位,僅支援Long、Double、Boolean、Keyword、Geo_point和Date類型。
Missing
當某行資料中的欄位為空白時,欄位值的預設值。
如果未設定Missing值,則在統計彙總時會忽略該行。
如果設定了Missing值,則使用Missing值作為欄位值的預設值參與統計彙總。
樣本
/** * 求所有的商品,產地一共來自多少個省份。 * 等效的SQL語句是SELECT count(distinct column_place) FROM product。 */ func distinctCount(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.TermQuery{"place_of_production", "浙江省"}). SetLimit(0). //如果只關心統計彙總結果,不關心具體資料,您可以將limit設定為0來提高效能。 Aggregation(search.NewDistinctCountAggregation("distinct_count_agg_1", "column_price").Missing(0.00))) searchResponse, err := client.Search(searchRequest) //執行查詢。 aggResults := searchResponse.AggregationResults //擷取統計彙總結果。 agg1, err := aggResults.DistinctCount("distinct_count_agg_1") //擷取名稱為"distinct_count_agg_1"的統計彙總結果。 if err != nil { panic(err) } fmt.Println(agg1.Value) //列印統計彙總結果。 }
欄位值分組
根據一個欄位的值對查詢結果進行分組,相同的欄位值放到同一分組內,返回每個分組的值和該值對應的個數。
當分組較大時,按欄位值分組可能會存在誤差。
參數
參數
說明
Name
自訂的統計彙總名稱,用於區分不同的統計彙總,可根據此名稱擷取本次統計彙總結果。
FieldName
用於統計彙總的欄位,僅支援Long、Double、Boolean、Keyword和Date類型。
Size
返回的分組數量,預設值為10。最大值為2000。當分組數量超過2000時,只會返回前2000個分組。
GroupBySorters
分組中的item定序,預設按照分組中item的數量降序排序,多個排序則按照添加的順序進行排列。支援的排序類型如下:
按照值的字典序升序排列
按照值的字典序降序排列
按照行數升序排列
按照行數降序排列
按照子統計彙總結果中值升序排列
按照子統計彙總結果中值降序排列
SubAggregation和SubGroupBy
子統計彙總,子統計彙總會根據分組內容再進行一次統計彙總分析。
情境
統計每個類別的商品數量,且統計每個類別價格的最大值和最小值。
方法
最外層的統計彙總是根據類別進行分組,再添加兩個子統計彙總求價格的最大值和最小值。
結果樣本
水果:5個(其中價格的最大值為15,最小值為3)
洗漱用品:10個(其中價格的最大值為98,最小值為1)
電子裝置:3個(其中價格的最大值為8699,最小值為2300)
其它:15個(其中價格的最大值為1000,最小值為80)
樣本
/** * 所有商品中每一個類別各有多少個,且統計每一個類別的價格最大值和最小值。 * 返回結果舉例:"水果:5個(其中價格的最大值為15,最小值為3),洗漱用品:10個(其中價格的最大值為98,最小值為1),電子裝置:3個(其中價格的最大值為8699,最小值為2300), * 其它:15個(其中價格的最大值為1000,最小值為80)"。 */ func GroupByField(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.MatchAllQuery{}). //匹配所有行。 SetLimit(0). GroupBy(search.NewGroupByField("group1", "column_type"). //按商品類別的欄位值進行分組。 SubAggregation(search.NewMinAggregation("min_price", "column_price")). //分組中最便宜的商品。 SubAggregation(search.NewMaxAggregation("max_price", "column_price")))) //分組中最貴的商品。 searchResponse, err := client.Search(searchRequest) if err != nil { fmt.Printf("%#v", err) return } groupByResults := searchResponse.GroupByResults //擷取統計彙總結果。 group, err := groupByResults.GroupByField("group1") if err != nil { fmt.Printf("%#v", err) return } for _, item := range group.Items { //遍曆返回的所有分組。 //列印分組的值和分組中的記錄行數。 fmt.Println("\tkey: ", item.Key, ", rowCount: ", item.RowCount) //列印價格的最小值。 minPrice, _ := item.SubAggregations.Min("min_price") if minPrice.HasValue() { fmt.Println("\t\tmin_price: ", minPrice.Value) } //列印價格的最大值。 maxPrice, _ := item.SubAggregations.Max("max_price") if maxPrice.HasValue() { fmt.Println("\t\tmax_price: ", maxPrice.Value) } } }
多欄位分組
根據多個欄位對查詢結果進行分組,支援使用token進行翻頁。
要實現多欄位分組,您可以通過欄位分組嵌套或者多欄位分組方式實現。關於兩種實現方式的功能對比,請參見附錄:多欄位分組不同實現方式對比。
參數
參數
說明
GroupByName
自訂的統計彙總名稱,用於區分不同的統計彙總,可根據此名稱擷取本次統計彙總結果。
SourceGroupByList
多列分組彙總欄位對象,最多支援設定32列。支援的分組類型如下:
重要Sources內分組類型的GroupBySorter僅支援groupKeySort,不支援subAggSort和rowCountSort。
預設降序排序。
當某一欄欄位值不存在時,系統會返回NULL。
欄位值分組GroupByField:僅支援設定GroupByName、FieldName和GroupBySorter參數。
長條圖統計GroupByHistogram:僅支援設定GroupByName、FieldName、Interval和GroupBySorter參數
日期長條圖統計GroupByDateHistogram:僅支援設定GroupByName、FieldName、Interval、TimeZone和GroupBySorter參數。
NextToken
進行翻頁時用於繼續擷取分組的Token值。多列的欄位值分組請求結果GroupByCompositeResult中會返回NextToken值,通過NextToken可翻頁擷取全量分組結果。
Size
返回分組的數量。當滿足條件的分組數量超過Size限制時,您可以通過NextToken繼續翻頁擷取分組。
重要當要限制返回的分組數量時,不支援同時配置Size和SuggestedSize參數。一般情況下只需配置Size參數即可。
如果是用於對接例如Spark、Presto等計算引擎的高吞吐情境,則只需配置SuggestedSize參數。
SuggestedSize
可設定為大於服務端最大限制的值或-1, 服務端按實際能力返回實際行數。適用於對接例如Spark、Presto等計算引擎的高吞吐情境。
當該值超過服務端最大值限制後會被修正為最大值。實際返回的分組結果數量為
min(suggestedSize, 服務端分組數量限制,總分組數量)
。SubAggList和SubGroupByList
子統計彙總,子統計彙總會根據分組內容再進行一次統計彙總分析。
重要GroupByComposite不支援作為SubGroupByList。
樣本
/** * 組合類別型分組彙總:根據傳入的多個SourceGroupBy(支援groupbyField、groupByHistogram和groupByDataHistogram)進行分組彙總 * 多列的彙總返回結果以扁平化結構返回。 */ func groupByComposite(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.MatchAllQuery{}). //匹配所有行。 SetLimit(0). GroupBy(search.NewGroupByComposite("groupByComposite"). SourceGroupBys(search.NewGroupByField("groupByField_1", "Col_Long"), search.NewGroupByField("groupByField_2", "Col_Keyword"), search.NewGroupByField("groupByField_3", "Col_Double")). SetSize(10))) searchResponse, err := client.Search(searchRequest) if err != nil { fmt.Printf("%#v", err) return } groupByResults := searchResponse.GroupByResults //擷取統計彙總結果。 group, err := groupByResults.GroupByComposite("group1") if err != nil { fmt.Printf("%#v", err) return } fmt.Println("groupName: ", group.Name) for _, item := range group.Items { //遍曆返回的所有分組。 //列印分組的值和分組中的記錄行數。 fmt.Printf("\tkey:") if item.Keys != nil { for i := 0; i < len(item.Keys); i++ { fmt.Printf(" %v ", *item.Keys[i]) } fmt.Printf("\trowCount:%v\n", item.RowCount) } } }
範圍分組
根據一個欄位的範圍對查詢結果進行分組,欄位值在某範圍內放到同一分組內,返回每個範圍中相應的item個數。
參數
參數
說明
Name
自訂的統計彙總名稱,用於區分不同的統計彙總,可根據此名稱擷取本次統計彙總結果。
FieldName
用於統計彙總的欄位,僅支援Long和Double類型。
Range(fromInclusive float64, toExclusive float64)
分組的範圍。
起始值fromInclusive可以使用最小值NegInf,結束值toExclusive可以使用最大值Inf。
SubAggregation和SubGroupBy
子統計彙總,子統計彙總會根據分組內容再進行一次統計彙總分析。
例如按銷量分組後再按省份分組,即可獲得某個銷量範圍內哪個省比重比較大,實現方法是GroupByRange下添加一個GroupByField。
樣本
/** * 求商品銷量時按[NegInf,1000)、[1000,5000)、[5000,Inf)這些分組計算每個範圍的銷量。 */ func GroupByRange(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.MatchAllQuery{}). //匹配所有行。 SetLimit(0). GroupBy(search.NewGroupByRange("group1", "column_number"). Range(search.NegInf, 1000). Range(1000, 5000). Range(5000, search.Inf))) searchResponse, err := client.Search(searchRequest) if err != nil { fmt.Printf("%#v", err) return } groupByResults := searchResponse.GroupByResults //擷取統計彙總結果。 group, err := groupByResults.GroupByRange("group1") if err != nil { fmt.Printf("%#v", err) return } for _, item := range group.Items { //遍曆返回的所有分組。 fmt.Println("\t[", item.From, ", ", item.To, "), rowCount: ", item.RowCount) //列印本次分組的行數。 } }
地理位置分組
根據距離某一個中心點的範圍對查詢結果進行分組,距離差值在某範圍內放到同一分組內,返回每個範圍中相應的item個數。
參數
參數
說明
Name
自訂的統計彙總名稱,用於區分不同的統計彙總,可根據此名稱擷取本次統計彙總結果。
FieldName
用於統計彙總的欄位,僅支援Geo_point類型。
CenterPoint(latitude float64, longitude float64)
起始中心點的經緯度。
latitude是起始中心點座標緯度,longitude是起始中心點座標經度。
Range(fromInclusive float64, toExclusive float64)
分組的範圍,單位為米。
起始值fromInclusive可以使用最小值NegInf,結束值toExclusive可以使用最大值Inf。
SubAggregation和SubGroupBy
子統計彙總,子統計彙總會根據分組內容再進行一次統計彙總分析。
樣本
/** * 求距離萬達廣場[NegInf,1000)、[1000,5000)、[5000,Inf)這些範圍內的人數,單位為米。 */ func GroupByGeoDistance(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.MatchAllQuery{}). //匹配所有行。 SetLimit(0). GroupBy(search.NewGroupByGeoDistance("group1", "Col_GeoPoint", search.GeoPoint{Lat: 30.137817, Lon:120.08681}). Range(search.NegInf, 1000). Range(1000, 5000). Range(5000, search.Inf))) searchResponse, err := client.Search(searchRequest) if err != nil { fmt.Printf("%#v", err) return } groupByResults := searchResponse.GroupByResults //擷取統計彙總結果。 group, err := groupByResults.GroupByGeoDistance("group1") if err != nil { fmt.Printf("%#v", err) return } for _, item := range group.Items { //遍曆返回的所有分組。 fmt.Println("\t[", item.From, ", ", item.To, "), rowCount: ", item.RowCount) //列印本次分組的行數。 } }
過濾條件分組
按照過濾條件對查詢結果進行分組,擷取每個過濾條件匹配到的數量,返回結果的順序和添加過濾條件的順序一致。
參數
參數
說明
Name
自訂的統計彙總名稱,用於區分不同的統計彙總,可根據此名稱擷取本次統計彙總結果。
Query
過濾條件,返回結果的順序和添加過濾條件的順序一致。
SubAggregation和SubGroupBy
子統計彙總,子統計彙總會根據分組內容再進行一次統計彙總分析。
樣本
/** * 按照過濾條件進行分組,例如添加三個過濾條件(銷量大於100、產地是浙江省、描述中包含杭州關鍵詞),然後擷取每個過濾條件匹配到的數量。 */ func GroupByFilter(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.MatchAllQuery{}). //匹配所有行。 SetLimit(0). GroupBy(search.NewGroupByFilter("group1"). Query(&search.RangeQuery{ FieldName: "number", From: 100, IncludeLower: true}). Query(&search.TermQuery{ FieldName: "place", Term: "浙江省", }). Query(&search.MatchQuery{ FieldName: "description", Text: "杭州", }))) searchResponse, err := client.Search(searchRequest) if err != nil { fmt.Printf("%#v", err) return } groupByResults := searchResponse.GroupByResults //擷取統計彙總結果。 group, err := groupByResults.GroupByFilter("group1") if err != nil { fmt.Printf("%#v", err) return } for _, item := range group.Items { //遍曆返回的所有分組。 fmt.Println("\trowCount: ", item.RowCount) //列印本次分組的行數。 } }
長條圖統計
按照指定資料間隔對查詢結果進行分組,欄位值在相同範圍內放到同一分組內,返回每個分組的值和該值對應的個數。
參數
參數
說明
GroupByName
自訂的統計彙總名稱,用於區分不同的統計彙總,可根據此名稱擷取本次統計彙總結果。
Field
用於統計彙總的欄位,僅支援Long和Double類型。
Interval
統計間隔。
FieldRange[min,max]
統計範圍,與Interval參數配合使用限制分組的數量。
(FieldRange.max-FieldRange.min)/Interval
的值不能超過2000。MinDocCount
最小行數。當分組中的行數小於最小行數時,不會返回此分組的統計結果。
Missing
當某行資料中的欄位為空白時,欄位值的預設值。
如果未設定missing值,則在統計彙總時會忽略該行。
如果設定了missing值,則使用missing值作為欄位值的預設值參與統計彙總。
樣本
func GroupByHistogram(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.MatchAllQuery{}). //匹配所有行。 SetLimit(0). GroupBy(search.NewGroupByHistogram("group1", "field_name"). SetMinDocCount(1). SetFiledRange(1, 100). SetMissing(3). SetInterval(10))) searchResponse, err := client.Search(searchRequest) if err != nil { fmt.Printf("%#v", err) return } groupByResults := searchResponse.GroupByResults //擷取統計彙總結果。 group, err := groupByResults.GroupByHistogram("group1") if err != nil { fmt.Printf("%#v", err) return } for _, item := range group.Items { //遍曆返回的所有分組。 fmt.Println("key:", item.Key.Value, ", rowCount:", item.Value) } }
日期長條圖統計
對日期欄位類型的資料按照指定間隔對查詢結果進行分組,欄位值在相同範圍內放到同一分組內,返回每個分組的值和該值對應的個數。
參數
參數
說明
GroupByName
自訂的統計彙總名稱,用於區分不同的統計彙總,可根據此名稱擷取本次統計彙總結果。
Field
用於統計彙總的欄位,僅支援Date類型。
Interval
統計間隔。
FieldRange[min,max]
統計範圍,與Interval參數配合使用限制分組的數量。
(FieldRange.max-FieldRange.min)/Interval
的值不能超過2000。MinDocCount
最小行數。當分組中的行數小於最小行數時,不會返回此分組的統計結果。
Missing
當某行資料中的欄位為空白時,欄位值的預設值。
如果未設定missing值,則在統計彙總時會忽略該行。
如果設定了missing值,則使用missing值作為欄位值的預設值參與統計彙總。
TimeZone
時區。格式為
+hh:mm
或者-hh:mm
,例如+08:00
、-09:00
。只有當欄位資料類型為Date時才需要配置。當Date類型欄位的Format未設定時區資訊時,可能會導致彙總結果存在N小時的位移,此時請設定TimeZone來解決該問題。
樣本
func GroupByDateHistogram(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.MatchAllQuery{}). //匹配所有行。 SetLimit(0). GroupBy(search.NewGroupByDateHistogram("date_group", "date_field_name"). SetMinDocCount(1). SetFiledRange("2017-05-01 10:00", "2017-05-21 13:00:00"). SetMissing("2017-05-01 13:01:00"). SetInterval(model.DateTimeValue{ Value: proto.Int32(1), Unit: model.DateTimeUnit_DAY.Enum(), }))) searchResponse, err := client.Search(searchRequest) if err != nil { fmt.Printf("%#v", err) return } groupByResults := searchResponse.GroupByResults //擷取統計彙總結果。 group, err := groupByResults.GroupByDateHistogram("date_group") if err != nil { fmt.Printf("%#v", err) return } for _, item := range group.Items { //遍曆返回的所有分組。 fmt.Printf("millisecondTimestamp:%d , rowCount:%d \n", item.Timestamp, item.RowCount) } }
嵌套
分組類型的統計彙總功能支援嵌套,其內部可以添加子統計彙總。
主要用於在分組內再次進行統計彙總,以兩層的嵌套為例:
GroupBy+SubGroupBy:按省份分組後再按照城市分組,擷取每個省份下每個城市的資料。
GroupBy+SubAggregation:按照省份分組後再求某個指標的最大值,擷取每個省的某個指標最大值。
為了效能、複雜度等綜合考慮,嵌套的層級只開放了一定的層數。更多資訊,請參見多元索引限制。
樣本
/**
* 嵌套的統計彙總樣本。
* 外層GroupByField中添加了2個Aggregation和1個GroupByRange。
*/
func NestedSample(client *tablestore.TableStoreClient, tableName string, indexName string) {
searchRequest := &tablestore.SearchRequest{}
searchRequest.
SetTableName(tableName). //設定資料表名稱。
SetIndexName(indexName). //設定多元索引名稱。
SetSearchQuery(search.NewSearchQuery().
SetQuery(&search.MatchAllQuery{}). //匹配所有行。
SetLimit(0).
GroupBy(search.NewGroupByField("group1", "field1").
SubAggregation(search.NewMinAggregation("sub_agg1", "sub_field1")).
SubAggregation(search.NewMaxAggregation("sub_agg2", "sub_field2")).
SubGroupBy(search.NewGroupByRange("sub_group1", "sub_field3").
Range(search.NegInf, 3).
Range(3, 5).
Range(5, search.Inf))))
searchResponse, err := client.Search(searchRequest)
if err != nil {
fmt.Printf("%#v", err)
return
}
groupByResults := searchResponse.GroupByResults //擷取統計彙總結果。
group, err := groupByResults.GroupByField("group1")
if err != nil {
fmt.Printf("%#v", err)
return
}
for _, item := range group.Items { //遍曆返回的所有分組。
//列印分組的值和分組中的記錄行數。
fmt.Println("\tkey: ", item.Key, ", rowCount: ", item.RowCount)
//擷取名稱為"sub_agg1"的統計彙總結果。
subAgg1, _ := item.SubAggregations.Min("sub_agg1")
if subAgg1.HasValue() {
fmt.Println("\t\tsub_agg1: ", subAgg1.Value)
}
//擷取名稱為"sub_agg2"的統計彙總結果。
subAgg2, _ := item.SubAggregations.Max("sub_agg2")
if subAgg2.HasValue() {
fmt.Println("\t\tsub_agg2: ", subAgg2.Value)
}
//擷取名稱為"sub_group1"的統計彙總結果。
subGroup, _ := item.SubGroupBys.GroupByRange("sub_group1")
for _, item := range subGroup.Items {
fmt.Println("\t\t[", item.From, ", ", item.To, "), rowCount: ", item.RowCount)
}
}
}
多個統計彙總
多個統計彙總功能可以組合使用。
當多個統計彙總的複雜度較高時可能會影響響應速度。
樣本1
func MultipleAggregations(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.MatchAllQuery{}). //匹配所有行。 SetLimit(0). Aggregation(search.NewAvgAggregation("agg1", "Col_Long")). //計算Col_Long欄位的平均值。 Aggregation(search.NewDistinctCountAggregation("agg2", "Col_Long")). //計算Col_Long欄位不同取值的個數。 Aggregation(search.NewMaxAggregation("agg3", "Col_Long")). //計算Col_Long欄位的最大值。 Aggregation(search.NewSumAggregation("agg4", "Col_Long")). //計算Col_Long欄位的和。 Aggregation(search.NewCountAggregation("agg5", "Col_Long"))) //計算存在Col_Long欄位的行數。 //設定返回所有列。 searchRequest.SetColumnsToGet(&tablestore.ColumnsToGet{ ReturnAll: true, }) searchResponse, err := client.Search(searchRequest) if err != nil { fmt.Printf("%#v", err) return } aggResults := searchResponse.AggregationResults //擷取統計彙總結果。 //擷取求平均值的統計彙總結果。 agg1, err := aggResults.Avg("agg1") //擷取名稱為"agg1"的統計彙總結果,類型為Avg。 if err != nil { panic(err) } if agg1.HasValue() { //名稱為"agg1"的統計彙總結果是否有Value值。 fmt.Println("(avg) agg1: ", agg1.Value) //列印Col_Long欄位平均值。 } else { fmt.Println("(avg) agg1: no value") //所有行都不存在Col_Long欄位時的列印資訊。 } //擷取去重統計行數的統計彙總結果。 agg2, err := aggResults.DistinctCount("agg2") //擷取名稱為"agg2"的統計彙總結果,類型為DistinctCount。 if err != nil { panic(err) } fmt.Println("(distinct) agg2: ", agg2.Value) //列印Col_Long欄位不同取值的個數。 //擷取求最大值的統計彙總結果。 agg3, err := aggResults.Max("agg3") //擷取名稱為"agg3"的統計彙總結果,類型為Max。 if err != nil { panic(err) } if agg3.HasValue() { fmt.Println("(max) agg3: ", agg3.Value) //列印Col_Long欄位最大值。 } else { fmt.Println("(max) agg3: no value") //所有行都不存在Col_Long欄位時的列印資訊。 } //擷取求和的統計彙總結果。 agg4, err := aggResults.Sum("agg4") //擷取名稱為"agg4"的統計彙總結果,類型為Sum。 if err != nil { panic(err) } fmt.Println("(sum) agg4: ", agg4.Value) //列印Col_Long欄位的和。 //擷取統計行數的統計彙總結果。 agg5, err := aggResults.Count("agg5") //擷取名稱為"agg5"的統計彙總結果,類型為Count。 if err != nil { panic(err) } fmt.Println("(count) agg6: ", agg5.Value) //列印存在Col_Long欄位的個數。 }
樣本2
func MultipleAggregationsAndGroupBysSample(client *tablestore.TableStoreClient, tableName string, indexName string) { searchRequest := &tablestore.SearchRequest{} searchRequest. SetTableName(tableName). //設定資料表名稱。 SetIndexName(indexName). //設定多元索引名稱。 SetSearchQuery(search.NewSearchQuery(). SetQuery(&search.MatchAllQuery{}). //匹配所有行。 SetLimit(0). Aggregation(search.NewAvgAggregation("agg1", "Col_Long")). //計算Col_Long欄位的平均值。 Aggregation(search.NewDistinctCountAggregation("agg2", "Col_Long")). //計算Col_Long欄位不同取值的個數。 Aggregation(search.NewMaxAggregation("agg3", "Col_Long")). //計算Col_Long欄位的最大值。 GroupBy(search.NewGroupByField("group1", "Col_Keyword"). //對Col_Keyword欄位做GroupByField取值統計彙總。 GroupBySorters([]search.GroupBySorter{}). //指定返回結果分組的順序。 Size(2). //僅返回前2個分組。 SubAggregation(search.NewAvgAggregation("sub_agg1", "Col_Long")). //對每個分組進行子統計彙總。 SubGroupBy(search.NewGroupByField("sub_group1", "Col_Keyword2"))). //對每個分組進行子統計彙總。 GroupBy(search.NewGroupByRange("group2", "Col_Long"). //對Col_Long欄位做GroupByRange範圍。 Range(search.NegInf, 3). //第一個分組包含Col_Long在(NegInf, 3)的索引行。 Range(3, 5). //第二個分組包含Col_Long在[3, 5)的索引行。 Range(5, search.Inf))) //第三個分組包含Col_Long在[5, Inf)的索引行。 // 設定返回所有列。 searchResponse, err := client.Search(searchRequest) if err != nil { fmt.Printf("%#v", err) return } aggResults := searchResponse.AggregationResults //擷取統計彙總結果。 //擷取求平均值的統計彙總結果。 agg1, err := aggResults.Avg("agg1") //擷取名稱為"agg1"的統計彙總結果,類型為Avg。 if err != nil { panic(err) } if agg1.HasValue() { //名稱為"agg1"的統計彙總結果是否有Value值。 fmt.Println("(avg) agg1: ", agg1.Value) //列印Col_Long欄位平均值。 } else { fmt.Println("(avg) agg1: no value") //所有行都不存在Col_Long欄位時的列印資訊。 } //擷取去重統計行數的統計彙總結果。 agg2, err := aggResults.DistinctCount("agg2") //擷取名稱為"agg2"的統計彙總結果,類型為DistinctCount。 if err != nil { panic(err) } fmt.Println("(distinct) agg2: ", agg2.Value) //列印Col_Long欄位不同取值的個數。 //擷取求最大值的統計彙總結果。 agg3, err := aggResults.Max("agg3") //擷取名稱為"agg3"的統計彙總結果,類型為Max。 if err != nil { panic(err) } if agg3.HasValue() { fmt.Println("(max) agg3: ", agg3.Value) //列印Col_Long欄位最大值。 } else { fmt.Println("(max) agg3: no value") //所有行都不存在Col_Long欄位時的列印資訊。 } groupByResults := searchResponse.GroupByResults //擷取統計彙總結果。 //擷取按欄位值分組的統計彙總結果。 group1, err := groupByResults.GroupByField("group1") //擷取名稱為"group1"的統計彙總結果,類型為GroupByField。 if err != nil { panic(err) } fmt.Println("group1: ") for _, item := range group1.Items { //遍曆返回的所有分組。 //item fmt.Println("\tkey: ", item.Key, ", rowCount: ", item.RowCount) //列印本次分組的行數。 //擷取求平均值的子統計彙總結果。 subAgg1, err := item.SubAggregations.Avg("sub_agg1") //擷取名稱為"sub_agg1"的子統計彙總結果,類型為Avg。 if err != nil { panic(err) } if subAgg1.HasValue() { //如果子統計彙總"sub_agg1"計算出了Col_Long欄位的平均值,則HasValue()返回true。 fmt.Println("\t\tsub_agg1: ", subAgg1.Value) //列印本次分組中,子統計彙總計算的Col_Long欄位的平均值。 } //擷取按欄位值分組的子統計彙總結果。 subGroup1, err := item.SubGroupBys.GroupByField("sub_group1") //擷取名稱為"sub_group1"的子統計彙總結果,類型為GroupByField。 if err != nil { panic(err) } fmt.Println("\t\tsub_group1") for _, subItem := range subGroup1.Items { //遍曆名稱為"sub_group1"的子統計彙總結果。 fmt.Println("\t\t\tkey: ", subItem.Key, ", rowCount: ", subItem.RowCount) //列印"sub_group1"的子統計彙總結果分組,即分組中的行數。 tablestore.Assert(subItem.SubAggregations.Empty(), "") tablestore.Assert(subItem.SubGroupBys.Empty(), "") } } //擷取按範圍分組的統計彙總結果。 group2, err := groupByResults.GroupByRange("group2") //擷取名稱為"group2"的統計彙總結果,類型為GroupByRange。 if err != nil { panic(err) } fmt.Println("group2: ") for _, item := range group2.Items { //遍曆返回的所有分組。 fmt.Println("\t[", item.From, ", ", item.To, "), rowCount: ", item.RowCount) //列印本次分組的行數。 } }
附錄:多欄位分組不同實現方式對比
如果要根據多個欄位對查詢結果進行分組,您可以通過欄位分組嵌套(即嵌套多層groupBy)或者多欄位分組(即直接使用GroupByComposite)功能實現。具體實現方式的功能對比說明請參見下表。
功能對比 | 欄位分組嵌套 | 多欄位分組 |
size | 2000 | 2000 |
欄位列限制 | 最高支援5層 | 最高支援32列 |
翻頁 | 不支援 | 支援通過GroupByComposite中的nextToken翻頁 |
分組中Item定序 |
| 按照值的字典序升序或降序排列 |
是否支援子統計彙總 | 支援 | 支援 |
相容性 | 日期類型根據format返回 | 日期類型返回時間戳記字串 |