Derivative aggregation
editDerivative aggregation
editA parent pipeline aggregation which calculates the derivative of a specified metric in a parent histogram (or date_histogram)
aggregation. The specified metric must be numeric and the enclosing histogram must have min_doc_count
set to 0
(default
for histogram
aggregations).
Syntax
editA derivative
aggregation looks like this in isolation:
"derivative": { "buckets_path": "the_sum" }
Table 61. derivative
Parameters
Parameter Name | Description | Required | Default Value |
---|---|---|---|
|
The path to the buckets we wish to find the derivative for (see |
Required |
|
|
The policy to apply when gaps are found in the data (see Dealing with gaps in the data for more details) |
Optional |
|
|
DecimalFormat pattern for the
output value. If specified, the formatted value is returned in the aggregation’s
|
Optional |
|
First Order Derivative
editThe following snippet calculates the derivative of the total monthly sales
:
resp = client.search( index="sales", size=0, aggs={ "sales_per_month": { "date_histogram": { "field": "date", "calendar_interval": "month" }, "aggs": { "sales": { "sum": { "field": "price" } }, "sales_deriv": { "derivative": { "buckets_path": "sales" } } } } }, ) print(resp)
response = client.search( index: 'sales', body: { size: 0, aggregations: { sales_per_month: { date_histogram: { field: 'date', calendar_interval: 'month' }, aggregations: { sales: { sum: { field: 'price' } }, sales_deriv: { derivative: { buckets_path: 'sales' } } } } } } ) puts response
const response = await client.search({ index: "sales", size: 0, aggs: { sales_per_month: { date_histogram: { field: "date", calendar_interval: "month", }, aggs: { sales: { sum: { field: "price", }, }, sales_deriv: { derivative: { buckets_path: "sales", }, }, }, }, }, }); console.log(response);
POST /sales/_search { "size": 0, "aggs": { "sales_per_month": { "date_histogram": { "field": "date", "calendar_interval": "month" }, "aggs": { "sales": { "sum": { "field": "price" } }, "sales_deriv": { "derivative": { "buckets_path": "sales" } } } } } }
|
And the following may be the response:
{ "took": 11, "timed_out": false, "_shards": ..., "hits": ..., "aggregations": { "sales_per_month": { "buckets": [ { "key_as_string": "2015/01/01 00:00:00", "key": 1420070400000, "doc_count": 3, "sales": { "value": 550.0 } }, { "key_as_string": "2015/02/01 00:00:00", "key": 1422748800000, "doc_count": 2, "sales": { "value": 60.0 }, "sales_deriv": { "value": -490.0 } }, { "key_as_string": "2015/03/01 00:00:00", "key": 1425168000000, "doc_count": 2, "sales": { "value": 375.0 }, "sales_deriv": { "value": 315.0 } } ] } } }
No derivative for the first bucket since we need at least 2 data points to calculate the derivative |
|
Derivative value units are implicitly defined by the |
|
The number of documents in the bucket are represented by the |
Second Order Derivative
editA second order derivative can be calculated by chaining the derivative pipeline aggregation onto the result of another derivative pipeline aggregation as in the following example which will calculate both the first and the second order derivative of the total monthly sales:
resp = client.search( index="sales", size=0, aggs={ "sales_per_month": { "date_histogram": { "field": "date", "calendar_interval": "month" }, "aggs": { "sales": { "sum": { "field": "price" } }, "sales_deriv": { "derivative": { "buckets_path": "sales" } }, "sales_2nd_deriv": { "derivative": { "buckets_path": "sales_deriv" } } } } }, ) print(resp)
response = client.search( index: 'sales', body: { size: 0, aggregations: { sales_per_month: { date_histogram: { field: 'date', calendar_interval: 'month' }, aggregations: { sales: { sum: { field: 'price' } }, sales_deriv: { derivative: { buckets_path: 'sales' } }, "sales_2nd_deriv": { derivative: { buckets_path: 'sales_deriv' } } } } } } ) puts response
const response = await client.search({ index: "sales", size: 0, aggs: { sales_per_month: { date_histogram: { field: "date", calendar_interval: "month", }, aggs: { sales: { sum: { field: "price", }, }, sales_deriv: { derivative: { buckets_path: "sales", }, }, sales_2nd_deriv: { derivative: { buckets_path: "sales_deriv", }, }, }, }, }, }); console.log(response);
POST /sales/_search { "size": 0, "aggs": { "sales_per_month": { "date_histogram": { "field": "date", "calendar_interval": "month" }, "aggs": { "sales": { "sum": { "field": "price" } }, "sales_deriv": { "derivative": { "buckets_path": "sales" } }, "sales_2nd_deriv": { "derivative": { "buckets_path": "sales_deriv" } } } } } }
And the following may be the response:
{ "took": 50, "timed_out": false, "_shards": ..., "hits": ..., "aggregations": { "sales_per_month": { "buckets": [ { "key_as_string": "2015/01/01 00:00:00", "key": 1420070400000, "doc_count": 3, "sales": { "value": 550.0 } }, { "key_as_string": "2015/02/01 00:00:00", "key": 1422748800000, "doc_count": 2, "sales": { "value": 60.0 }, "sales_deriv": { "value": -490.0 } }, { "key_as_string": "2015/03/01 00:00:00", "key": 1425168000000, "doc_count": 2, "sales": { "value": 375.0 }, "sales_deriv": { "value": 315.0 }, "sales_2nd_deriv": { "value": 805.0 } } ] } } }
Units
editThe derivative aggregation allows the units of the derivative values to be specified. This returns an extra field in the response
normalized_value
which reports the derivative value in the desired x-axis units. In the below example we calculate the derivative
of the total sales per month but ask for the derivative of the sales as in the units of sales per day:
resp = client.search( index="sales", size=0, aggs={ "sales_per_month": { "date_histogram": { "field": "date", "calendar_interval": "month" }, "aggs": { "sales": { "sum": { "field": "price" } }, "sales_deriv": { "derivative": { "buckets_path": "sales", "unit": "day" } } } } }, ) print(resp)
response = client.search( index: 'sales', body: { size: 0, aggregations: { sales_per_month: { date_histogram: { field: 'date', calendar_interval: 'month' }, aggregations: { sales: { sum: { field: 'price' } }, sales_deriv: { derivative: { buckets_path: 'sales', unit: 'day' } } } } } } ) puts response
const response = await client.search({ index: "sales", size: 0, aggs: { sales_per_month: { date_histogram: { field: "date", calendar_interval: "month", }, aggs: { sales: { sum: { field: "price", }, }, sales_deriv: { derivative: { buckets_path: "sales", unit: "day", }, }, }, }, }, }); console.log(response);
POST /sales/_search { "size": 0, "aggs": { "sales_per_month": { "date_histogram": { "field": "date", "calendar_interval": "month" }, "aggs": { "sales": { "sum": { "field": "price" } }, "sales_deriv": { "derivative": { "buckets_path": "sales", "unit": "day" } } } } } }
And the following may be the response:
{ "took": 50, "timed_out": false, "_shards": ..., "hits": ..., "aggregations": { "sales_per_month": { "buckets": [ { "key_as_string": "2015/01/01 00:00:00", "key": 1420070400000, "doc_count": 3, "sales": { "value": 550.0 } }, { "key_as_string": "2015/02/01 00:00:00", "key": 1422748800000, "doc_count": 2, "sales": { "value": 60.0 }, "sales_deriv": { "value": -490.0, "normalized_value": -15.806451612903226 } }, { "key_as_string": "2015/03/01 00:00:00", "key": 1425168000000, "doc_count": 2, "sales": { "value": 375.0 }, "sales_deriv": { "value": 315.0, "normalized_value": 11.25 } } ] } } }