![]() Главная страница Случайная страница КАТЕГОРИИ: АвтомобилиАстрономияБиологияГеографияДом и садДругие языкиДругоеИнформатикаИсторияКультураЛитератураЛогикаМатематикаМедицинаМеталлургияМеханикаОбразованиеОхрана трудаПедагогикаПолитикаПравоПсихологияРелигияРиторикаСоциологияСпортСтроительствоТехнологияТуризмФизикаФилософияФинансыХимияЧерчениеЭкологияЭкономикаЭлектроника |
Аппроксимация табличной функции методом Лагранжа
Постановка задачи:
Пусть величина y является некоторой функцией аргумента x, но её невозможно записать в виде некоторой формулы, или эта формула очень громоздка и трудна в работе, но при этом задана таблица:
Необходимо найти приближённое значение этой функции в некоторой точке x.
Аппроксимирующую функцию будем искать в следующем виде:
Для упрощения подсчётов используем таблицу Лагранжа:
Исходные данные:
Функция для проверки: y=tg(cos(x)).
Алгоритм решения:
1) Задать N – количество узлов данных (N=8)
2) Задать исходные данные к задаче: float X[N] = {..,..,..,..,..,..,..,.., }; float Y[N] = {..,..,..,..,..,..,..,.., };
3) Формирование матрицы Лагранжа: н. ц. i = 0, n н. ц. j = i+1, n aij = xi-xj aji = -aij к. ц. j к. ц. i
4) Ввод z.
5) Завершение формирования матрицы, заполн. диагональ: н. ц. i = 0, n aii =z-xj к. ц. i
6) Вывести A.
7) Вычисление P: P=1 н. ц. i=0, n P=P*aii к. ц. i
8) Вычисление ki н. ц. i=0, n ki=1 н. ц. j=0, n ki=ki*aij к. ц. j к. ц. i 9) Вычисление Ln:
10) Вывести Ln.
11) Проверка: y=f(z) y ≈ N
Текст программы:
#include< iostream.h> #include< math.h> #include< stdio.h> #include< conio.h>
float *X, *Y, **V; float *B, p=1, z=2.499; int n, i, j, k, pr=0; void init(int q=1) { if(q) {X=new float [n]; Y=new float [n]; V=new float *[n]; for(i=0; i< n; i++) V[i]=new float[n]; B=new float [n]; } else {delete[] X; delete[] Y; for(i=0; i< n; i++) delete[] V[i]; delete[] V; delete[] B; } } void ex(void) { n=8; pr=1; init(1); float X1[8]={0.1, 0.3, 0.5, 0.7, 0.9, 1.1, 1.3, 1.5}; float Y1[8]={1.540, 1.414, 1.204, 0.960, 0.716, 0.487, 0.274, 0.017}; cout< < " \nVvod x[8]: "; for(i=0; i< n; i++) { X[i]=X1[i]; printf(" %.1f ", X[i]); } cout< < " \n\nVvod y[8]: "; for(i=0; i< n; i++) { Y[i]=Y1[i]; printf(" %.3f ", Y[i]); } cout< < endl; } void lagr(void) { for(i=0; i< n; i++) for(j=i+1; j< n; j++) { V[i][j]=X[i]-X[j]; V[j][i]=-V[i][j]; } } void lagr1(void) { for(i=0; i< n; i++) V[i][i]=(z-X[i]); } void prbr(void) { float h=1; for(i=0; i< n; i++) { for(j=0; j< n; j++) h*=V[i][j]; B[i]=h; h=1; p*=V[i][i]; } } float P(void) { float s=0; for(i=0; i< n; i++) s+=(Y[i]/B[i]); return s*p; }
void S(void) { for(i=0; i< n; i++) { cout< < endl; for(j=0; j< n; j++) printf(" %.3f ", V[i][j]); }
}
void main(void) { clrscr(); textmode(2); cout< < " Vvod 0 "; gotoxy(10, 1); cin> > n; if(n==0) ex(); else { init(); cout< < " Vvod x[" < < n< < " ] "; for(i=0; i< n; i++) cin> > X[i]; cout< < " Vvod y[" < < n< < " ] "; for(i=0; i< n; i++) cin> > Y[i]; } lagr(); //S();
cout< < " \nVvod x: "; cin> > z;
lagr1(); prbr(); P(); cout< < " \nf(" < < z< < ")=" < < P(); if(pr) cout< < " \n\nProverka: tg(cos(" < < z< < "))=" < < sin(cos(z))/cos(cos(z)); init(0); getch(); }
Скриншот результата программы (при x=0, 4):
Результаты работы программы и проверка (проверка говорит о том, что решение правильное):
f(0, 4) = 1, 316353
Если сравнить результаты аппроксимации табличной функции методом неопределённых коэффициентов (методом Вандермонда) и методом Лагранжа, то результаты почти совпадают (можно даже сказать, что совпадают). Скриншот результата программы (при x=1, 2):
Результаты работы программы и проверка (проверка говорит о том, что решение правильное):
f(1, 2) = 0, 37965
|