/** * 3次方程式の実根を1個だけ求める。 * 4字方程式で使う。 * @param i_b * @param i_c * @param i_d * @param o_result * @return */ private static double solve3Equation_1(double i_b, double i_c, double i_d) { double tmp, b, p, q; b = i_b / (3); p = b * b - i_c / 3; q = (b * (i_c - 2 * b * b) - i_d) / 2; if ((tmp = q * q - p * p * p) == 0) { // 重根 q = NyARMath.cubeRoot(q); return(2 * q - b); } else if (tmp > 0) { // 実根1,虚根2 double a3 = NyARMath.cubeRoot(q + ((q > 0) ? 1 : -1) * Math.Sqrt(tmp)); double b3 = p / a3; return(a3 + b3 - b); } else { // 実根3 tmp = 2 * Math.Sqrt(p); double t = Math.Acos(q / (p * tmp / 2)); return(tmp * Math.Cos(t / 3) - b); } }
/** * この関数は、3次方程式(x^3+b*x^2+c*x+d=0)の実根を計算します。 * このコードは、http://aoki2.si.gunma-u.ac.jp/JavaScript/src/3jisiki.htmlを元にしています。 * @param i_b * X^2の係数 * @param i_c * X^1の係数 * @param i_d * X^0の係数 * @param o_result * 実根。double[3]を指定すること。 * @return * 返却した実根の数。 */ public static int solve3Equation(double i_b, double i_c, double i_d, double[] o_result) { double tmp, b, p, q; b = i_b / (3); p = b * b - i_c / 3; q = (b * (i_c - 2 * b * b) - i_d) / 2; if ((tmp = q * q - p * p * p) == 0) { // 重根 q = NyARMath.cubeRoot(q); o_result[0] = 2 * q - b; o_result[1] = -q - b; return(2); } else if (tmp > 0) { // 実根1,虚根2 double a3 = NyARMath.cubeRoot(q + ((q > 0) ? 1 : -1) * Math.Sqrt(tmp)); double b3 = p / a3; o_result[0] = a3 + b3 - b; // 虚根:-0.5*(a3+b3)-b,Math.abs(a3-b3)*Math.sqrt(3.0)/2 return(1); } else { // 実根3 tmp = 2 * Math.Sqrt(p); double t = Math.Acos(q / (p * tmp / 2)); o_result[0] = tmp * Math.Cos(t / 3) - b; o_result[1] = tmp * Math.Cos((t + 2 * Math.PI) / 3) - b; o_result[2] = tmp * Math.Cos((t + 4 * Math.PI) / 3) - b; return(3); } }