// Copyright 2015 The Prometheus Authors // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. package promql import ( "fmt" "math" "testing" "github.com/stretchr/testify/require" ) func TestKahanSumInc(t *testing.T) { testCases := map[string]struct { first float64 second float64 expected float64 }{ "+Inf + anything = +Inf": { first: math.Inf(1), second: 2.0, expected: math.Inf(1), }, "-Inf + anything = -Inf": { first: math.Inf(-1), second: 2.0, expected: math.Inf(-1), }, "+Inf + -Inf = NaN": { first: math.Inf(1), second: math.Inf(-1), expected: math.NaN(), }, "NaN + anything = NaN": { first: math.NaN(), second: 2, expected: math.NaN(), }, "NaN + Inf = NaN": { first: math.NaN(), second: math.Inf(1), expected: math.NaN(), }, "NaN + -Inf = NaN": { first: math.NaN(), second: math.Inf(-1), expected: math.NaN(), }, } runTest := func(t *testing.T, a, b, expected float64) { t.Run(fmt.Sprintf("%v + %v = %v", a, b, expected), func(t *testing.T) { sum, c := kahanSumInc(b, a, 0) result := sum + c if math.IsNaN(expected) { require.Truef(t, math.IsNaN(result), "expected result to be NaN, but got %v (from %v + %v)", result, sum, c) } else { require.Equalf(t, expected, result, "expected result to be %v, but got %v (from %v + %v)", expected, result, sum, c) } }) } for name, testCase := range testCases { t.Run(name, func(t *testing.T) { runTest(t, testCase.first, testCase.second, testCase.expected) runTest(t, testCase.second, testCase.first, testCase.expected) }) } }