github.com/go-graphite/carbonapi@v0.17.0/expr/functions/powSeries/function.go (about) 1 package powSeries 2 3 import ( 4 "context" 5 "math" 6 7 "github.com/go-graphite/carbonapi/expr/helper" 8 "github.com/go-graphite/carbonapi/expr/interfaces" 9 "github.com/go-graphite/carbonapi/expr/types" 10 "github.com/go-graphite/carbonapi/pkg/parser" 11 ) 12 13 type powSeries struct{} 14 15 func GetOrder() interfaces.Order { 16 return interfaces.Any 17 } 18 19 func New(_ string) []interfaces.FunctionMetadata { 20 res := make([]interfaces.FunctionMetadata, 0) 21 22 f := &powSeries{} 23 functions := []string{"powSeries"} 24 for _, n := range functions { 25 res = append(res, interfaces.FunctionMetadata{Name: n, F: f}) 26 } 27 28 return res 29 } 30 31 func (f *powSeries) Do(ctx context.Context, eval interfaces.Evaluator, e parser.Expr, from, until int64, values map[parser.MetricRequest][]*types.MetricData) ([]*types.MetricData, error) { 32 series, err := helper.GetSeriesArgs(ctx, eval, e.Args(), from, until, values) 33 if err != nil { 34 return nil, err 35 } 36 37 overallLength := -1 38 largestSeriesIdx := -1 39 for i, s := range series { 40 l := len(s.GetValues()) 41 if l > overallLength { 42 overallLength = l 43 largestSeriesIdx = i 44 } 45 } 46 47 r := series[largestSeriesIdx].CopyName("powSeries(" + e.RawArgs() + ")") 48 r.Values = make([]float64, 0) 49 50 seriesValues := make([][]float64, 0, len(series)) 51 for _, s := range series { 52 seriesValues = append(seriesValues, s.GetValues()) 53 } 54 55 for i := 0; i < overallLength; i++ { 56 first := true 57 var result float64 58 59 for _, vals := range seriesValues { 60 var val float64 61 if i < len(vals) { 62 val = vals[i] 63 } else { 64 val = math.NaN() 65 } 66 67 if first { 68 result = val 69 first = false 70 } else { 71 result = math.Pow(result, val) 72 } 73 } 74 75 if math.IsInf(result, 0) { 76 result = math.NaN() 77 } 78 r.Values = append(r.Values, result) 79 } 80 81 return []*types.MetricData{r}, nil 82 } 83 84 func (f *powSeries) Description() map[string]types.FunctionDescription { 85 return map[string]types.FunctionDescription{ 86 "powSeries": { 87 Description: "Takes two or more series and pows their points. A constant line may be used.", 88 Function: "powSeries(*seriesLists)", 89 Group: "Combine", 90 Module: "graphite.render.functions", 91 Name: "powSeries", 92 Params: []types.FunctionParam{ 93 { 94 Multiple: true, 95 Name: "seriesLists", 96 Required: true, 97 Type: types.SeriesList, 98 }, 99 }, 100 }, 101 } 102 }