В табл. 3 приведено
сравнение методов хорд, бисекции и
метода Ньютона для расчета корня.
- корень, высчитанный по методу ‘*’,
– количество итераций, затраченное на
приближение корня методом ‘*’, где ‘*’
принимает значения: H
– метод хорд, B
– метод бисекции и N
– метод Ньютона.
Проанализировав результаты применения метода Ньютона, можно сказать, что при расчете данной функции он дает очень хорошие результаты, и сходится за минимальное среди рассмотренных методов число итераций, которое соответствует теоретическому значению порядка.
По
результатам эксперимента по определению
обусловленности метода Ньютона можно
оценить абсолютную обусловленность
как значение примерно равное
,
что говорит об очень хорошей обусловленности
метода.
Проанализировав данные вычислительного эксперимента по трем методам: Ньютона, хорд и бисекции, можно сделать вывод, что для данной функции метод Ньютона сходится наиболее быстрым образом и имеет преимущество перед рассмотренными в сравнении методами. Из недостатков метода можно выделить необходимость расчета аналитической формулы первой производной функции, и значения второй производной.
Таблица 3 – Сравнение методов Ньютона, хорд и бисекции
|
Значение
|
Значение
|
Значение
|
Значение
|
Значение
|
Значение
|
Значение
|
Значение
|
|
0.1 |
0.001 |
0.875 |
0.858529 |
0.872102 |
2 |
3 |
2 |
|
0.01 |
0.001 |
0.863281 |
0.865001 |
0.867114 |
6 |
4 |
3 |
|
0.001 |
0.001 |
0.867676 |
0.867002 |
0.867114 |
9 |
5 |
3 |
|
0.0001 |
0.001 |
0.866943 |
0.867002 |
0.867114 |
9 |
5 |
3 |
|
0.00001 |
0.001 |
0.866943 |
0.867002 |
0.867114 |
9 |
5 |
3 |
|
0.000001 |
0.001 |
0.866943 |
0.867002 |
0.867114 |
9 |
5 |
3 |
|
0.1 |
0.0001 |
0.875 |
0.858435 |
0.872037 |
2 |
3 |
2 |
|
0.01 |
0.0001 |
0.863281 |
0.864908 |
0.867108 |
6 |
4 |
3 |
|
0.001 |
0.0001 |
0.867676 |
0.866953 |
0.867108 |
9 |
6 |
3 |
|
0.0001 |
0.0001 |
0.867126 |
0.867086 |
0.867108 |
12 |
8 |
3 |
|
0.00001 |
0.0001 |
0.867081 |
0.867086 |
0.867078 |
13 |
8 |
4 |
|
0.000001 |
0.0001 |
0.876081 |
0.867086 |
0.867078 |
13 |
8 |
4 |
|
0.1 |
0.00001 |
0.875 |
0.858425 |
0.872045 |
2 |
3 |
2 |
|
0.01 |
0.00001 |
0.863281 |
0.864907 |
0.867107 |
6 |
4 |
3 |
|
0.001 |
0.00001 |
0.867676 |
0.866949 |
0.867107 |
9 |
6 |
3 |
|
0.0001 |
0.00001 |
0.867126 |
0.867075 |
0.867107 |
12 |
8 |
3 |
|
0.00001 |
0.0001 |
0.867092 |
0.867084 |
0.86786 |
16 |
9 |
4 |
|
0.000001 |
0.0001 |
0.867084 |
0.867084 |
0.86786 |
17 |
9 |
4 |
#include <stdio.h>
#include <math.h>
#include <stdlib.h>
#include <iostream>
#include <conio.h>
double delta;
#ifndef __NEWTON
#define __NEWTON
#endif
#ifndef M_PI
#define M_PI 3.14159265358979323846
#endif // !M_PI
#ifndef FF(x)
#define FF(x) ( (M_PI * pow(x, M_PI + 7) + 2 * M_PI*pow(x, M_PI + 3) + M_PI * pow(x, M_PI - 1) + 4 * pow(x, 3)) / (pow(x, 8) + 2 * pow(x, 4) + 1) )
#define FFF(x) ( (PI2*pow(x, M_PI + 10) - M_PI * pow(x, M_PI + 10) + 3 * PI2*pow(x, M_PI + 6) - 3 * M_PI*pow(x, M_PI + 6) + 3 * PI2*pow(x, M_PI + 2) - 3 * M_PI*pow(x, M_PI + 2) - 20 * pow(x, 6) + PI2 * pow(x, M_PI - 2) - M_PI*pow(x,M_PI-2) + 12 * pow(x, 2)) / (pow(x, 12) + 3 * pow(x, 8) + 3 * pow(x, 4) + 1) )
#endif
extern double F(double);
/******************************************************************/
/* Функция F(X) , задаваемая пользователем */
/******************************************************************/
#ifdef __NEWTON
extern double F1(double);
/******************************************************************/
/* Производная функции F(X) , задаваемая пользователем */
/******************************************************************/
#endif
#ifdef __ITER
extern double PHI(double);
/******************************************************************/
/* Функция PHI(X) , задаваемая пользователем */
/* Данная функция используется в методе */
/* простых итераций */
/******************************************************************/
#endif
double Round(double, double);
/******************************************************************/
/* Функция Round (X, Delta) , предназначена для округления */
/* X с точностью Delta */
/******************************************************************/
double BISECT(double, double, double, int&);
/******************************************************************/
/* Функция BISECT предназначена для решения уравнения F(X)=0 */
/* методом деления отрезка пополам. Использованы обозначения: */
/* Left - левый конец промежутка */
/* Right - правый конец промежутка */
/* Eps - погрешность вычисления корня уравнения; */
/* N - число итераций */
/******************************************************************/
double ITER(double, double, int&);
/******************************************************************/
/* Функция ITER предназначена для решения уравнения F(X)=X */
/* методом простой итерации. Использованы обозначения: */
/* X0 - начальное приближение корня */
/* Eps - погрешность вычисления корня уравнения; */
/* N - число итераций */
/******************************************************************/
double HORDA(double, double, double, int&);
/******************************************************************/
/* Функция HORDA предназначена для решения уравнения F(x)=0 */
/* методом хорд. Использованы обозначения: */
/* Left - левый конец промежутка */
/* Right - правый конец промежутка */
/* Eps - погрешность вычисления корня уравнения; */
/* N - число итераций */
/******************************************************************/
double NEWTON(double, double, int&);
/******************************************************************/
/* Функция NEWTON предназначена для решения уравнения F(X)=0 */
/* методом касательных. Использованы обозначения: */
/* X - начальное приближение корня */
/* Eps - погрешность вычисления корня уравнения; */
/* N - число итераций */
/******************************************************************/
double Round(double X, double Delta) {
if (Delta <= 1E-9) {
puts("Неверное задание точности округления\n");
exit(1);
}
if (X > 0.0) {
return Delta * long(X / Delta + 0.5);
} else {
return Delta * long(X / Delta - 0.5);
}
}
double F(double x) {
// функция f(x)
extern double delta;
double s;
long S;
s = pow(x, M_PI) - 1/(pow(x,4)+1);
s = Round(s, delta);
return s;
}
double F1(double x) {
// функция f'(x)
double f = (M_PI * pow(x, M_PI + 7) + 2 * M_PI*pow(x, M_PI + 3) + M_PI * pow(x, M_PI - 1) + 4 * pow(x, 3)) / (pow(x, 8) + 2 * pow(x, 4) + 1);
return f;
}
double PHI(double x) {
// функция φ(x) - для метода простых итераций
return x;
}
double BISECT(double Left, double Right, double Eps, int &N) {
double E = fabs(Eps) * 2.0;
double FLeft = F(Left);
double FRight = F(Right);
double X = 0.5 * (Left + Right);
double Y;
if (FLeft * FRight > 0.0) {
puts("Неверное задание интервала\n");
exit(1);
}
if (Eps <= 0.0) {
puts("Неверное задание точности\n");
exit(1);
}
if (FLeft == 0.0) {
return Left;
}
if (FRight == 0.0) {
return Right;
}
for (N = 0; Right - Left >= E; N++) {
X = 0.5 * (Right + Left); // вычисление середины отрезка
Y = F(X);
if (Y == 0.0) {
return X;
}