| complex-newton.C |
1 /*
2 * complex-newton.cpp -- Newton 法で方程式 f(x)=0 を解く
3 * コンパイル: g++ -o complex-newton complex-newton.cpp
4 * 実行: ./complex-newton
5 */
6
7 #include <iostream>
8 #include <complex>
9
10 int main(void)
11 {
12 int i, maxitr = 100;
13 std::complex<double> x, dx;
14 std::complex<double> f(std::complex<double>), dfdz(std::complex<double>);
15 double eps;
16
17 std::cout << " 初期値 x0, 許容精度ε=";
18 std::cin >> x >> eps;
19
20 std::cout.precision(16);
21 for (i = 0; i < maxitr; i++) {
22 dx = - f(x) / dfdz(x);
23 x += dx;
24 std::cout << "f(" << x << ")=" << f(x) << std::endl;
25 if (abs(dx) <= eps) break;
26 }
27 return 0;
28 }
29
30 /*
31 * この関数の例は杉原・室田『数値計算法の数理』岩波書店, p.67 による
32 * f(z) = z^3-2z+2
33 * 1実根(≒-1.769292354238631),2虚根(≒0.8846461771193157±0.5897428050222054)
34 * を持つが、原点の近くに初期値を取ると、0 と 1 の間を振動する。
35 * --- という意味のことを書いてあるけれど、相当な暴れ馬。ぜひ遊んでみよう。
36 */
37
38 std::complex<double> f(std::complex<double> z)
39 {
40 /* return z * z * z - 2 * z + 2; */
41 return z * (z * z - 2.0) + 2.0;
42 }
43
44 /* 関数 f の導関数 (df/dx のつもりで名前をつけた) */
45 std::complex<double> dfdz(std::complex<double> z)
46 {
47 return 3.0 * z * z - 2.0;
48 }
|
| complex-newton 実行結果 |
% g++ complex-newton.cpp % ./a.out 初期値 x0, 許容精度ε=(0.07,0.07) 1e-15 f((1.000479890500462,0.01402105439035678))=(0.9998905285720316,0.01405867910352982) f((0.008690071144917044,0.08327942929892811))=(1.982439704951537,-0.1671175729050391) f((0.9899874424723547,0.002680506223014176))=(0.9902658531083521,0.002520260799472426) f((-0.06300187281112724,0.01783194417259117))=(2.125813775994601,-0.03545722093219378) f((1.00568580973205,-0.003615972418678629))=(1.005743530042432,-0.00373963422208404) (中略) f((0.9999999999999999,1.517769664024309e-319))=(1,1.517769664024309e-319) f((-9.992007221626409e-16,9.106617984145856e-319))=(2.000000000000002,-1.821323596829171e-318) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) f((0.9999999999999999,0))=(1,0) f((-9.992007221626409e-16,0))=(2.000000000000002,0) % |