x^1 + x ^2 +...+x ^n = m 求x

版权声明:本文为博主原创文章,转载请注明出处,谢谢 https://blog.csdn.net/supercooly/article/details/53176613

一、问题描述

x+x^1+x^2+…x^12 = 100,求 x

二、公式求解

x^1 + x ^2 +…+x ^n = m
x^2 + x ^3 +…+x ^(n+1) = mx
两边同时乘 x,相减

x - x ^(n + 1) = m - mx
(x - x ^(n + 1) ) /(1 - x) = m

这个方程没有精确解,只有近似解。关于各种变换,然后手工求解,至少得过了高数6级,抱歉我没过,所有用计算机了

三、Java 求近似解

import org.junit.Test;

public class QiuXDemo {

    @Test
    public void test() {
        double x1 = qiujie(12, 200, 0.000001);
        double x2 = qiujie(12, 200, 0.00000001);
        System.out.println("最终结果精度0.000001  \t x = " + x1);
        System.out.println("最终结果精度0.00000001 \t x = " + x2);
    }

    /**
     * @描述:x * ( sum - 1 - x ^ n ) = sum
     * 
     * @param n
     * @param sum
     * @return double @createTime:2016年11月15日
     */
    private double qiujie(final int n, final double sum, final double errorRange) {
        if (n == 1) {
            return sum;
        }
        int xInt = 1;
        int sumInt = 0;
        while (sumInt < sum) {
            sumInt = 0;
            for (int tempN = 1; tempN <= n; tempN++) {
                sumInt += Math.pow(xInt, tempN);
            }
            // System.out.println("求和 xInt = " + xInt + ",sumInt = " + sumInt);
            if (sumInt > sum) {
                // System.out.println("找到了整形的上界");
                break;
            }
            // 找到结果了
            if (sumInt == sum) {
                // System.out.println("找到了整形的结果");
                return xInt;
            }
            xInt++;
        }
        // 上界与下界之间,二分法继续寻找近似解
        return getNearX(n, sum, xInt - 1, xInt, errorRange);
    }

    private double getNearX(final int n, final double sum, double lowX, double highX, final double errorRange) {

        double nearX = (lowX + highX) / 2;
        if (lowX >= highX) {
            System.out.println("上界不大于下界,不找了 lowX = " + lowX + ", highX = " + highX);
            return nearX;
        }
        double sumDouble = (nearX - Math.pow(nearX, n + 1)) / (1 - nearX);
        // System.out.println("正在计算 近似值 nearX = " + nearX + ", 求和 sumDouble = "
        // + sumDouble);
        if (Math.abs(sumDouble - sum) < errorRange) {
            System.out.println("找到指定精度内的数字了,不找了 lowX = " + lowX + ", highX = " + highX);
            return nearX;
        }
        if (sumDouble > sum) {
            highX = nearX;
        } else {
            lowX = nearX;
        }
        // System.out.println("继续查找 lowX = "+ lowX +", highX = " +highX);
        return getNearX(n, sum, lowX, highX, errorRange);
    }

}

猜你喜欢

转载自blog.csdn.net/supercooly/article/details/53176613