@@ -866,6 +866,19 @@ which incur interpreter overhead.
866866 window.append(x)
867867 yield math.sumprod(kernel, window)
868868
869+ def polynomial_eval(coefficients, x):
870+ """Evaluate a polynomial at a specific value.
871+
872+ Computes with better numeric stability than Horner's method.
873+ """
874+ # Evaluate x³ -4x² -17x + 60 at x = 2.5
875+ # polynomial_eval([1, -4, -17, 60], x=2.5) --> 8.125
876+ n = len(coefficients)
877+ if n == 0:
878+ return x * 0 # coerce zero to the type of x
879+ powers = accumulate(repeat(x, n - 1), operator.mul, initial=1)
880+ return math.sumprod(reversed(coefficients), powers)
881+
869882 def polynomial_from_roots(roots):
870883 """Compute a polynomial's coefficients from its roots.
871884
@@ -1245,6 +1258,37 @@ which incur interpreter overhead.
12451258 >>> list (convolve(data, [1 , - 2 , 1 ]))
12461259 [20, 0, -36, 24, -20, 20, -20, -4, 16]
12471260
1261+ >>> from fractions import Fraction
1262+ >>> from decimal import Decimal
1263+ >>> polynomial_eval([1 , - 4 , - 17 , 60 ], x = 2 )
1264+ 18
1265+ >>> x = 2 ; x** 3 - 4 * x** 2 - 17 * x + 60
1266+ 18
1267+ >>> polynomial_eval([1 , - 4 , - 17 , 60 ], x = 2.5 )
1268+ 8.125
1269+ >>> x = 2.5 ; x** 3 - 4 * x** 2 - 17 * x + 60
1270+ 8.125
1271+ >>> polynomial_eval([1 , - 4 , - 17 , 60 ], x = Fraction(2 , 3 ))
1272+ Fraction(1274, 27)
1273+ >>> x = Fraction(2 , 3 ); x** 3 - 4 * x** 2 - 17 * x + 60
1274+ Fraction(1274, 27)
1275+ >>> polynomial_eval([1 , - 4 , - 17 , 60 ], x = Decimal(' 1.75' ))
1276+ Decimal('23.359375')
1277+ >>> x = Decimal(' 1.75' ); x** 3 - 4 * x** 2 - 17 * x + 60
1278+ Decimal('23.359375')
1279+ >>> polynomial_eval([], 2 )
1280+ 0
1281+ >>> polynomial_eval([], 2.5 )
1282+ 0.0
1283+ >>> polynomial_eval([], Fraction(2 , 3 ))
1284+ Fraction(0, 1)
1285+ >>> polynomial_eval([], Decimal(' 1.75' ))
1286+ Decimal('0.00')
1287+ >>> polynomial_eval([11 ], 7 ) == 11
1288+ True
1289+ >>> polynomial_eval([11 , 2 ], 7 ) == 11 * 7 + 2
1290+ True
1291+
12481292 >>> polynomial_from_roots([5 , - 4 , 3 ])
12491293 [1, -4, -17, 60]
12501294 >>> factored = lambda x : (x - 5 ) * (x + 4 ) * (x - 3 )
0 commit comments