ЛАБОРАТОРНАЯ РАБОТА № 5 (1-1)
Решение системы нелинейных уравнений методом Ньютона
Рассмотрим общий случай – решение системы n нелинейных уравнений с n неизвестными
F(x)=0,
где ,
Будем предполагать отображение непрерывно
дифференцируемо в некоторой окрестности решения z, так что
Обозначим - матрица Якоби системы в точке
.
Вообще говоря, метод решения системы нелинейных уравнений имеет много общего с методом решения одного нелинейного уравнения. В случае одного нелинейного уравнения метод Ньютона аппроксимирует его линейным уравнением, полученным использованием первых двух членов ряда Тейлора. Так же можно поступить и в случае системы n уравнений.
Пусть - текущее приближение к
решению z системы F(x)=0. Тогда в
точке
можно записать разложение в ряд Тейлора:
Рассмотри первые два члена ряда Тейлора.
Получаем аппроксимацию нелинейных функций:
Для определения следующего приближения к решению будем использовать нуль линейной
аппроксимации, то есть положим нулю правую часть нашего равенства; получим
систему линейных уравнений:
; или
Эту систему можно решить при помощи метода Гаусса. Из
этой системы находим p, а новое приближение к решению получаем по формуле , то есть
- формула метода
Ньютона.
Обозначим . Пусть при некоторых
, выполняются условия:
1) при
2) при
Обозначим также ,
,
-
евклидова норма в
Теорема (о сходимости метода Ньютона)
При
условиях 1), 2) и итерационный процесс Ньютона
сходится с оценкой погрешности
#include "stdafx.h"
#include <math.h>
#include <conio.h>
// Количество уравнений
const n = 2;
void GaussSolve (float a[n][n],float b[n],float x[n]);
float Norm (float x[n]);
float f1(float x[n]);
float f2(float x[n]);
float df1_dx(float x[n]);
float df1_dy(float x[n]);
float df2_dx(float x[n]);
float df2_dy(float x[n]);
typedef float (*lpFunction)(float* f);
const float a = 1.0f;
const float b = 7.5f;
int main(int argc, char* argv[])
{
int i,j, iter=0;
// Точность
float eps = 1e-5;
printf ("%s","Решение системы нелинейных уравнений методом Ньютона\n");
printf ("Точность вычислений: %f\n",eps);
// Матрица
float a[n][n];
// Вектор правых частей
float b[n];
// Вектор решения
float x[n], xk[n],p[n];
lpFunction Jacobi[n][n];
Jacobi[0][0] = df1_dx; Jacobi[0][1] = df1_dy;
Jacobi[1][0] = df2_dx; Jacobi[1][1] = df2_dy;
// Выбираем начальное приближение
xk[0]=1.5;xk[1]=7;
do
{
iter++;
for (i=0;i<n;i++)
{
x[i] = xk[i];
}
// Заполняем матрицу A
for (i=0;i<n;i++)
for (j=0;j<n;j++)
{
a[i][j] = Jacobi[i][j](x);
};
// Заполняем вектор правых частей
b[0]=-f1(x); b[1]=-f2(x);
GaussSolve (a,b,p);
// Получаем следующее приближение, складывая предыдущее и вновь полученное
for (i=0;i<n;i++)
{
xk[i] = x[i] + p[i];
}
}
while (fabs(Norm (x) - Norm(xk))>=eps);
printf ("%s","Вектор решения: [ ");
for (i=0;i<n;i++)
{
printf ("%f ",xk[i]);
}
printf ("%s","]\n");
Уважаемый посетитель!
Чтобы распечатать файл, скачайте его (в формате Word).
Ссылка на скачивание - внизу страницы.