Untitled
unknown
plain_text
2 years ago
7.4 kB
9
Indexable
// Includem bibliotecile necesare
#include <iostream>
#include <math.h>
#include <stdio.h>
#include <stdlib.h>
using namespace std;
// Declaram constanta numarului maxim de iteratii permise
const int MAX_ITERATIONS=1000;
double(*f)(double), (*fn)(double), (*fd)(double);
// Prima functie a)
double f1(double x) {
return log10(1+x)+x-1.5;
}
// A doua functie b)
double f2(double x) {
return pow(x,3)+(25*x)-37;
}
// Derivata primei functii
double fd1(double x) {
return (1/(1+x)*log(10));
}
// Derivata celei de-al doilea functii
double fd2(double x) {
return 3*pow(x,2)+25;
}
// Forma echivalenta a primei ecuatii alesa in mod special
// ca sa satisfaca conditia suficienta de convergenta
double phi1(double x) {
return 1.5-log10(1+x);
}
// Forma echivalenta a celei de-a doilea ecuatii alesa in mod
// special ca sa satisfaca conditia suficienta de convergenta
double phi2(double x) {
return (pow(x,3)-37)/25;
}
// Metoda aproximatiilor succesive
void SITER() {
// Initiam contorul iteratiilor
int k=0;
// Declaram variabilele necesare
// inclusiv eroarea epsilon=10^(-6)
double x0,x1,eps=0.000001;
cout<<"Introduceti valoarea initiala x0=";
cin>>x0;
// Deschidem un ciclu infinit
while(1) {
x1=fn(x0);
// Incrementam contorul iteratiilor
k++;
// Verificam daca metoda converge
if(abs(x1-x0)<eps) {
cout<<"Radacina este: "<<x0<<endl;
cout<<"Numarul de iteratii: "<<k<<endl;
break;
}
// Adaugam verificarea pentru cazul in care metoda nu converge
if(k>MAX_ITERATIONS) {
cout<<"Eroare! Metoda nu converge dupa "<<MAX_ITERATIONS<<" iteratii."<<endl;
break;
}
x0=x1;
}
}
// Metoda injumatatirii intervalului (bisectiei)
void BISECT() {
// Initiam contorul iteratiilor
int k=0;
// Declaram variabilele necesare
// inclusiv exactitatea epsilon=10^(-2)
double a,b,c=0,eps=0.01;
cout<<"Introduceti intervalul:"<<endl;
cout<<"a=";
cin>>a;
cout<<"b=";
cin>>b;
// Deschidem instructiunea repetitiva ciclica cu conditia
// ca c aproximeaza radacina r cu eroarea dorita
while(abs(b-a)>=eps) {
// Incrementam contorul iteratiilor
k++;
// Operatia de injumatatire (recomandata)
// ce nu ne scoate in afara intervalului
c=a+((b-a)/2);
// Verificam convergenta
if(k>MAX_ITERATIONS) {
cout<<"Eroare! Metoda nu a convergat dupa "<<MAX_ITERATIONS<<" iteratii!"<<endl;
return;
}
// Valoarea c este chiar radacina cautata
if(f(c)==0)
break;
// Daca radacina reala se gaseste in intervalul [a,c] acolo unde
// functia ia valori de semne contrare la capetele intervalului
else if(f(a)*f(c)<0)
b=c;
// Daca radacina reala se gaseste in intervalul [c,b] acolo unde
// functia ia valori de semne contrare la capetele intervalului
else if(f(c)*f(b)<0)
a=c;
else {
// Afisam mesajul de eroare daca metoda nu converge
cout<<"Metoda nu converge! Alege alt interval sau schimba functia"<<endl;
return;
}
}
cout<<"Radacina este: "<<c<<endl;
cout<<"Numarul de iteratii: "<<k<<endl;
}
// Metoda tangentelor (Newton)
void NEWTON() {
// Initiam contorul iteratiilor
int k=0;
// Declaram variabilele necesare
// inclusiv precizia epsilon=10^(-6)
double x0,x1,eps=0.000001;
cout<<"Introduceti valoarea initiala x0=";
cin>>x0;
// Deschidem un ciclu pentru iteratii
while(k<MAX_ITERATIONS) {
x1=x0-f(x0)/fd(x0);
// Incrementam contorul iteratiilor
k++;
if(abs(x1-x0)<eps) {
cout<<"Radacina este: "<<x0<<endl;
cout<<"Numarul de iteratii: "<<k<<endl;
break;
}
x0=x1;
}
// Verificam daca metoda a convergat
if(k==MAX_ITERATIONS) {
cout<<"Eroare! Metoda nu a convergat dupa "<<MAX_ITERATIONS<<" iteratii!"<<endl;
cout<<"Incercati cu o alta valoare initiala x0"<<endl;
cout<<"Sau verificati functia f si derivata fd"<<endl;
}
}
// Metoda secantelor
void SECANT() {
// Initiam contorul iteratiilor
int k=0;
// Declaram variabilele necesare
// inclusiv exactitatea epsilon=10^(-6)
double x1,x2,x3=0,y,eps=0.000001;
cout<<"Introduceti intervalul:"<<endl;
cout<<"a=";
cin>>x1;
cout<<"b=";
cin>>x2;
do {
// Incrementam contorul iteratiilor
k++;
y=x3;
// Forma recomandata a formulei (evita neutralizarea termenilor)
x3=x2-(f(x2)*(x2-x1)/(f(x2)-f(x1)));
x1=x2;
x2=x3;
// Verificam daca metoda converge
if(k>MAX_ITERATIONS) {
cout<<"Eroare! Metoda secantelor nu converge"<<endl;
cout<<"in numarul maxim de iteratii permis!"<<endl;
return;
}
} while(fabs(y-x3)>=eps);
cout<<"Radacina este: "<<x3<<endl;
cout<<"Numarul de iteratii: "<<k<<endl;
}
// Metoda de selectare a functiei
void selectFunction() {
cout<<"1) log10(1+x)+x-1.5"<<endl;
cout<<"2) pow(x,3)+(25*x)-37"<<endl;
// Declaram variabila optiunii selectate
int opt;
cout<<"Introduceti optiunea: ";
do {
opt=getchar();
} while(opt<'1' || opt>'2');
// Efectuam atribuirile necesare (dupa caz)
switch(opt) {
case'1': {
f=f1; // functia
fn=phi1; // echivalenta
fd=fd1; // derivata
break;
}
case'2': {
f=f2; // functia
fn=phi2; // echivalenta
fd=fd2; // derivata
break;
}
}
}
// Functia de selectare (meniu)
int meniu() {
if(f==f1)
cout<<"Functia curenta selectata: log10(1+x)+x-1.5\n"<<endl;
else
cout<<"Functia curenta selectata: pow(x,3)+(25*x)-37\n"<<endl;
cout<<"1. Selecatarea altei functii"<<endl;
cout<<"2. Metoda aproximatiei succesive"<<endl;
cout<<"3. Metoda injumatatirii intervalului (bisectiei)"<<endl;
cout<<"4. Metoda tangentelor (Newton)"<<endl;
cout<<"5. Metoda secantelor"<<endl;
cout<<"6. Iesire din program\n"<<endl;
// Declaram variabila optiunii selectate
int opt;
cout<<"Introduceti optiunea: ";
do {
opt=getchar();
} while(opt<'1' || opt>'6');
return opt-'0';
}
// Programul principal
int main() {
// Declaram variabila optiunii selectate
int opt;
// Stabilim prima ecuatie ca selectata
f=f1; // functia
fn=phi1; // echivalenta
fd=fd1; // derivata
do {
switch(opt=meniu()) {
case 1: {
selectFunction();
break;
}
case 2: {
SITER();
break;
}
case 3: {
BISECT();
break;
}
case 4: {
NEWTON();
break;
}
case 5: {
SECANT();
break;
}
}
} while(opt!=6);
}Editor is loading...
Leave a Comment