如何统计普通形式与Horner法求多项式的乘法次数并返回计数?
多项式求值乘法次数统计方案
问题核心
你当前用静态变量统计乘法次数的方式存在两个问题:一是静态变量会在多次调用后累计数值,无法保证测试独立性;二是无法直接将计数结果返回给测试环境。下面提供两种可行的解决思路:
方案1:自定义结果类(推荐)
创建一个包含求值结果和乘法次数的类,作为方法返回值,让测试环境能直接获取这两个数据。
自定义结果类代码
public class PolyEvalResult { private final double result; private final int multiplicationCount; public PolyEvalResult(double result, int multiplicationCount) { this.result = result; this.multiplicationCount = multiplicationCount; } // Getter方法供外部获取数据 public double getResult() { return result; } public int getMultiplicationCount() { return multiplicationCount; } }
普通形式求值改造(准确统计乘法次数)
注意:原代码用Math.pow(x,n)会隐藏内部的乘法操作,必须手动计算x^n才能统计真实的总乘法次数。
public static PolyEvalResult evalSimple(double[] a, double x) { double y = a[0]; int count = 0; int n = 1; for (int i = 1; i < a.length; ++i) { // 手动计算x的n次方,统计每一次乘法 double xPower = 1; for (int j = 0; j < n; j++) { xPower *= x; count++; } // 统计系数与x^n相乘的操作 y += a[i] * xPower; count++; n++; } return new PolyEvalResult(y, count); }
Horner法实现(带计数)
public static PolyEvalResult evalHorner(double[] a, double x) { double y = a[a.length - 1]; int count = 0; for (int i = a.length - 2; i >= 0; --i) { y = y * x + a[i]; count++; // 每次循环仅1次乘法 } return new PolyEvalResult(y, count); }
方案2:用数组传递计数(轻量方案)
如果不想创建新类,可以用长度为1的int数组作为参数,方法内部修改数组元素的值,测试环境通过数组读取计数。
普通形式改造代码
public static double evalSimple(double[] a, double x, int[] countHolder) { double y = a[0]; countHolder[0] = 0; // 每次调用重置计数,避免累计 int n = 1; for (int i = 1; i < a.length; ++i) { double xPower = 1; for (int j = 0; j < n; j++) { xPower *= x; countHolder[0]++; } y += a[i] * xPower; countHolder[0]++; n++; } return y; }
测试调用示例
public static void main(String[] args) { double[] coeffs = {1, 2, 3, 4}; // 对应多项式:1 + 2x + 3x² + 4x³ double x = 2; // 方案1调用 PolyEvalResult simpleRes = evalSimple(coeffs, x); PolyEvalResult hornerRes = evalHorner(coeffs, x); System.out.println("普通法结果:" + simpleRes.getResult() + ",乘法次数:" + simpleRes.getMultiplicationCount()); System.out.println("Horner法结果:" + hornerRes.getResult() + ",乘法次数:" + hornerRes.getMultiplicationCount()); // 方案2调用 int[] count = new int[1]; double simpleVal = evalSimple(coeffs, x, count); System.out.println("普通法结果:" + simpleVal + ",乘法次数:" + count[0]); }
关键结论
- 普通法的总乘法次数为
n(n+1)/2 - 1(n为多项式项数),Horner法固定为n-1次,项数越多Horner法的效率优势越明显。 - 静态变量不适合测试场景,会导致多次调用的计数累加,破坏测试独立性。
内容的提问来源于stack exchange,提问作者Bogdan Klinowitzki
相关产品推荐
相关产品推荐

