ES6.0.0官方參考指南翻譯~指標聚合~Percentiles Aggregation

Percentiles Aggregation

這是一種多值指標聚合,用於計算聚合文檔提取數值的1個或多個百分位統計數據.

這些值既可通過文檔的特定字段提取,也可通過腳本來生成.

Percentiles通常用於查找異常值.

在正態分佈中,0.13%和99.87%表示與平均值的三個標準差。

任何超出三個標準差的數據通常被視為異常。

當檢索到一系列百分位數時,可使用它們來評估數據的分佈情況,並確定數據是否存在偏斜/雙峰等。

假設你的數據由網頁加載時間所構成. 平均和中值加載時間對管理員來說,並無多大用處. 最大值可能很有用,但它會被慢響應所扭曲.

下面讓我們查一下加載時間的百分位數範圍:

GET latency/data/_search

{

"size": 0,

"aggs" : {

"load_time_outlier" : {

"percentiles" : {

"field" : "load_time" #1

}

}

}

}

1 load_time字段必須是數值字段

默認情況下, percentile指標會生成一組百分位: [ 1, 5, 25, 50, 75, 95, 99 ].

其響應類似於:

{

...

"aggregations": {

"load_time_outlier": {

"values" : {

"1.0": 9.9,

"5.0": 29.500000000000004,

"25.0": 167.5,

"50.0": 445.0,

"75.0": 722.5,

"95.0": 940.5,

"99.0": 980.1000000000001

}

}

}

}

正如上面所展示的,聚合返回默認範圍內每個百分位的統計值。如果我們假設響應時間的單位是毫秒,那麼很明顯網頁一般都會在10-723毫秒內加載完畢,但偶爾加載時間到達到941-980毫秒。

通過,管理員只對極端數值感興趣.因此,可以在請求中指定我們感興趣的百分位(請求百分位必須在 0-100之間):

GET latency/data/_search

{

"size": 0,

"aggs" : {

"load_time_outlier" : {

"percentiles" : {

"field" : "load_time",

"percents" : [95, 99, 99.9] #1

}

}

}

}

1.使用percents參數來指定要計算的百分位

Keyed Response(分組響應/按鍵響應)

默認keyed為true,該標誌會將不同字符串鍵與每個桶進行關聯,並以hash形式(非數組)來返回百分位結果. 將keyed設為false,可禁用這種行為:

GET latency/data/_search

{

"size": 0,

"aggs": {

"load_time_outlier": {

"percentiles": {

"field": "load_time",

"keyed": false

}

}

}

}

響應:

{

...

"aggregations": {

"load_time_outlier": {

"values": [

{

"key": 1.0,

"value": 9.9

},

{

"key": 5.0,

"value": 29.500000000000004

},

{

"key": 25.0,

"value": 167.5

},

{

"key": 50.0,

"value": 445.0

},

{

"key": 75.0,

"value": 722.5

},

{

"key": 95.0,

"value": 940.5

},

{

"key": 99.0,

"value": 980.1000000000001

}

]

}

}

}

Script

百分位指標聚合也支持腳本。例如,如果加載時間單位是毫秒,但我們想以秒來計算百分位計算,則可使用腳本來修改:

GET latency/data/_search

{

"size": 0,

"aggs" : {

"load_time_outlier" : {

"percentiles" : {

"script" : {

"lang": "painless",

"source": "doc['load_time'].value / params.timeUnit", #1

"params" : {

"timeUnit" : 1000 #2

}

}

}

}

}

}

1 field參數已被script參數所替換,即使用腳本來計算百分位數值

2 與其它腳本一樣,它也支持參數化輸入

這會使用painless腳本語言來將script參數解析為內聯腳本(不帶腳本參數)。

可通過如下語法來使用存儲腳本:

GET latency/data/_search

{

"size": 0,

"aggs" : {

"load_time_outlier" : {

"percentiles" : {

"script" : {

"id": "my_script",

"params": {

"field": "load_time"

}

}

}

}

}

}

百分位數是近似值

有多種算法可計算百分位數值. 簡單的實現方式是將所有值存儲在排序數組中。

在查找50th百分位數值,你只需要查找my_array[count(my_array) * 0.5]中的最後一個值.

很顯然,上述簡單實現不具備擴展性—排序數組會隨著數據集數量線性增長。

要計算Elasticsearch集群中潛在數十億個值的百分位數,只能計算其近似百分位數。

百分位指標使用的算法稱為TDigest (可參考Ted Dunning的Computing Accurate Quantiles using T-Digests).

使用此指標時,須注意以下幾條規則:

  • 精度與q(1-q)成正比.也就是說,極端百分位數(例如99%)比不太極端的百分位數(例如中位數)更準確.
  • 對於較小的值集,百分位數非常準確(如果數據足夠小,則可能100%準確)。
  • 隨著桶內數據增加,算法的準確性會下降(近似百分位數)。 它有效地節省了內存的交易準確性。準確性到底是多少,這很難評估,因為它取決於數據分佈和聚合的數據量。

下圖顯示了均勻分佈的相對誤差,具體取決於所收集的數據數量和請求的百分位數:

ES6.0.0官方參考指南翻譯~指標聚合~Percentiles Aggregation

它顯示了極端百分位數的精度更好。 大量值誤差較小的原因在於,大數定律使得值的分佈越來越均勻,並且t-digest樹在總結它時可以做得更好。 對於更偏斜的分佈,情況就不是這樣了。

壓縮

近似算法必須平衡內存利用率和估算的準確性。 可以使用compression參數來控制此平衡:

GET latency/data/_search

{

"size": 0,

"aggs" : {

"load_time_outlier" : {

"percentiles" : {

"field" : "load_time",

"tdigest": {

"compression" : 200 #1

}

}

}

}

}

1 控制內存使用和近似錯誤

TDigest算法會使用許多“節點”來估算百分位數 - 可用節點越多,與數據量成正比的準確度(以及內存佔用量)就越高。compression參數將最大節點數限制為20 * compression。

因此,通過增加壓縮值,則可以犧牲更多的內存來提高百分位數的準確性。

但,過大的壓縮值會使算法變慢,因為底層樹數據結構的大小會增加,從而導致更昂貴的操作。

默認壓縮值為100。每個“節點”使用大約32個字節的內存,因此在最壞情況下,默認設置將產生大約64KB的TDigest。 在實踐中,數據分佈往往更隨機,因此TDigest消耗的內存會少些。

HDR Histogram

注意

此設置公開了HDR直方圖的內部實現,其語法可能會在將來發生變化。

HDR Histogram (High Dynamic Range Histogram) 是另一種替代實現,在計算延遲測量的百分位數時非常有用,因為它的實現比t-digest更快,但同時消耗的內存也更大。此實現能保持固定的最壞情況百分比錯誤(指定為有效位數)。也就是說,如果在直方圖中以1微秒到1小時(3600000000微秒)的值記錄數據,並將其設置為3個有效數字,則對於高達1毫秒的值,其值分辨率將保持為1微秒;對於最大跟蹤值(1小時),其值分辨率將保持為3.6秒(或更好)。

可在請求中指定方法參數來使用HDR Histogram:

GET latency/data/_search

{

"size": 0,

"aggs" : {

"load_time_outlier" : {

"percentiles" : {

"field" : "load_time",

"percents" : [95, 99, 99.9],

"hdr": { #1

"number_of_significant_value_digits" : 3 #2

}

}

}

}

}

1 hdr對象表示應使用HDR Histogram 來計算百分位數,並且可以在對象內指定此算法的特殊設置。

2 number_of_significant_value_digits可用來指定直方圖分辨率的有效位數。

HDR Histogram只支持正值,如果傳遞負值,則會出錯。 如果值的範圍未知,則最好不要使用HDR Histogram,因為這可能會導致非常高的內存消耗。

Missing value

missing 參數用於定義如何處理文檔中的缺失值。

默認,它會忽略缺失值,但也可以將其視為有值字段。

GET latency/data/_search

{

"size": 0,

"aggs" : {

"grade_percentiles" : {

"percentiles" : {

"field" : "grade",

"missing": 10 #1

}

}

}

}

1 對於無值的grade字段,其所屬文檔會與值為0的文檔放在同一個桶內。

全部指標聚合,請參考

單值指標聚合

多值指標聚合

地理位置相關聚合

可執行Map-Reduce計算的聚合


分享到:


相關文章: