Docsity
Docsity

Prepara tus exámenes
Prepara tus exámenes

Prepara tus exámenes y mejora tus resultados gracias a la gran cantidad de recursos disponibles en Docsity


Consigue puntos base para descargar
Consigue puntos base para descargar

Gana puntos ayudando a otros estudiantes o consíguelos activando un Plan Premium


Orientación Universidad
Orientación Universidad


Métodos Numéricos y Probabilidad, Ejercicios de Métodos Computacionales

Trabajo de métodos numéricos interpolador de newton

Tipo: Ejercicios

2019/2020

Subido el 17/04/2020

andrei-jaimes
andrei-jaimes 🇨🇴

1 documento

1 / 21

Toggle sidebar

Esta página no es visible en la vista previa

¡No te pierdas las partes importantes!

bg1
Universidad Industrial de Santander
Facultad de ciencias
Escuela de Física
Proyecto Nº1
Andrei Jaimes Motta
Grupo: B1- 25439
Métodos Numéricos y Probabilidad
Presentado a:
Prof. ILIA DAVIDOVICH MIKHAILOV
Bucaramanga
2014
pf3
pf4
pf5
pf8
pf9
pfa
pfd
pfe
pff
pf12
pf13
pf14
pf15

Vista previa parcial del texto

¡Descarga Métodos Numéricos y Probabilidad y más Ejercicios en PDF de Métodos Computacionales solo en Docsity!

Universidad Industrial de Santander Facultad de ciencias Escuela de Física

Proyecto Nº

Andrei Jaimes Motta

Grupo: B1- 25439 Métodos Numéricos y Probabilidad

Presentado a: Prof. ILIA DAVIDOVICH MIKHAILOV

Bucaramanga

2014

1. Problemas para Tarea N 1 (raíces de una ecuación algebraica)

Considere la ecuación ( ) dentro del intervalo ( ) con un parámetro p que se varía dentro del intervalo. Las funciones (^ )^ y parámetros están dados en la tabla. Denotaremos las raíces de esta ecuación ( ) donde n es el número total de las raíces.

a) Análisis gráfico para separar las raíces.

La función a la cual se le van a hallar las raíces es:

( ) ( ) , Con

Es necesario tener en cuenta el comportamiento matemático de estas dos funciones. Para observar dicho comportamiento se requiere realizar un análisis gráfico, donde se representaran con diferente color las dos funciones respectivamente, teniendo en cuenta que los cruces o interceptos entre las funciones son las raíces que se quieren hallar numéricamente. Cabe anotar que estos métodos numéricos funcionan en intervalos donde solo se encuentra una raíz, así que se debe calcular un paso h que cumpla esta condicione.

Para este caso se tomó , donde se aprecia que sin importar el valor que se le dé a p ,

h (paso) siempre es un intervalo que contiene una única raíz (figura 1)

Para el caso de la figura 1, donde se tomó p = 0.5, el valor del paso h = , lo cual cumple lo dicho anteriormente, encerrando solo el valor de una raíz, así para cada una de las raíces de esta función. El recuadro Evaluación muestra el punto de intersecto entre las dos funciones, lo cual concuerda con los valores hallados mediante el método numérico. Según la gráfica se podría decir que esto no cumple para valores en los cuales los interceptos se hagan muy cercanos a cero o al paso, debido a que no es apreciable a simple vista, pero si realizamos un zoom a la función (figura 2), en uno de estos puntos, se corrobora que el paso sigue cumpliendo la condición de una sola raíz en su intervalo.

Figura 3. Grafica para p= 5.0. La línea punteada representa la primera raíz.

b) Utilizando el método de bisección encuentre el número n de raíces y valores de todas raíces con la precisión para valores del parámetro y.

El código del programa se realizó en lenguaje C, usando el compilador Code::Blocks 13.12.

#include<stdio.h> #include<math.h>

double fun(double x); double Raiz(double a,double b,double tol); int main(){ double pi=3.1415926,p=5.0; double a=0,b=20.0,tol=pow(10,-8),h=pi/(2*p),xl,xr,yl,yr,xraiz; int cont=0,i;

FILE *fdat1; fdat1=fopen("Punto1b_5.0.dat","w"); xl=a; xr=a+h; fprintf(fdat1,"%2s %6s \n","n","raíz");

while(xr<b){ yl=fun(xl); yr=fun(xr); if(yl*yr<0.0){ cont++; xraiz=Raiz(xl,xr,tol); fprintf(fdat1,"%2d %6lf\n",cont,xraiz); } xl=xr; yl=yr; xr=xl+h; yr=fun(xr); } fclose(fdat1); return 0; }

//Función a la cual se le van a encontrar las raíces double fun(double x){ double y,p=5.0; y=exp(-px)-sin(px); return y; }

Figura 4. Gráfica del número de raíces n en función del parámetro p, aumentando en intervalos de 0.225.

El código del programa se realizó en lenguaje C, usando el compilador Code::Blocks 13.12.

#include<stdio.h> #include<math.h> double fun(double x,double p); double Raiz(double a,double b,double p,double tol); void allraiz(double a,double b,double p,double tol,double hraiz,int *nraiz,double xraiz[1000]); int main(){ double a=0.0,b=20.0,p0=0.5,pf=5.0,p,tol=pow(10,-8),hraiz=0.001,xraiz[1000],hp; int nraiz,i,np=21,j;

FILE fdat1; fdat1=fopen("cantidad de raices.dat","w"); hp=(pf-p0)/(np-1); for(j=1;j<=np;j++){ p=p0+(j-1)hp;

//Llamada de la subrutina allraiz

allraiz(a,b,p,tol,hraiz,&nraiz,xraiz);

//Impresión de las raíces para cada valor de p en el archivo "cantidad de raices.dat" fprintf(fdat1,"%9lf %3d\n",p,nraiz); }

fclose(fdat1); return 0; } //Función externa double fun(double x, double p){ double y; y=exp(-px)-sin(px); return y; }

/La función Raiz busca la solución de la ecuación F(x)= dentro del intervalo (a,b) con la precisión tol, usando el método de bisección/ double Raiz(double a,double b,double p,double tol){ double xl,xr,fl,fr,x,f; xl=a; fl=fun(xl,p); xr=b; fr=fun(xr,p); x=(xl+xr)/2.0; f=fun(x,p); while(f!=0 && (xr-xl)>tol){ if(f*fl<0){ xr=x; fr=f; } else{ xl=x; fl=f; } x=(xl+xr)/2.0; f=fun(x,p); } return x; }

#include<stdio.h> #include<math.h> double fun(double x,double p); double dfun(double x,double p); double ddfun(double x,double p); double bisec(double a,double b,double p,double eps,int *nit); double newt(double a,double b,double p,double eps,int *nit);

int main(){ double a=0.0,b=20.0,p0=0.5,pf=5.0,p,eps=pow(10,- 8),hraiz=0.001,xraiz1,xraiz2,hp,xl,xr,fl,fr,xlu,xru; int nraiz=0,i,nit1,nit2; hp=(pf-p0)/9; //hp=1.0; FILE fdat1; fdat1=fopen("raices dif_metodos.txt","w"); fprintf(fdat1,"%6s %6s %12s %4s %12s %4s\n","p","#raiz","raiz bisecc","#it","raiz newton","#it"); for(i=1;i<=10;i++){ p=p0+(i-1)hp; nraiz=0; xl=a; xr=a+hraiz; fl=fun(xl,p); fr=fun(xr,p); xlu=xl; xru=xl; while(xr<b){ if(fl*fr<0){ nraiz++; xlu=xl; xru=xr; } xl=xr; fl=fr; xr=xl+hraiz; fr=fun(xr,p); } xraiz1=bisec(xlu,xru,p,eps,&nit1); xraiz2=newt(xlu,xru,p,eps,&nit2); fprintf(fdat1,"%6.2lf %6d %12.7lf %4d %12.7lf %4d\n",p,nraiz,xraiz1,nit1,xraiz2,nit2);

fclose(fdat1); return 0; } //Funcion original double fun(double x, double p){ double y; y=exp(-px)-sin(px); return y; } //Primera derivada de la funcion original double dfun(double x,double p){ double y; y=-pexp(-px)-pcos(px); return y; } //segunda derivada de la funcion original double ddfun(double x,double p){ double y; y=(pp)exp(-px)+(pp)sin(px); return y; }

//Funcion que halla las raices mediante el metodo de biseccion double bisec(double a,double b,double p,double eps,int *nit){ double xl,xr,fl,fr,x,f; xl=a; fl=fun(xl,p); xr=b; fr=fun(xr,p); x=(xl+xr)/2.0; f=fun(x,p); nit=0; while(f!=0 && (xr-xl)>eps){ if(ffl<0){ xr=x; fr=f; } else{ xl=x; fl=f;

Tabla2. Valores de la función con precisión =0. i xi yi 1 0 0 2 0.314159 0. 3 0.628319 0. 4 0.942478 0. 5 1.256637 0. 6 1.570796 0. 7 1.884956 0. 8 2.199115 0. 9 2.513274 0. 10 2.827433 0. 11 3.141593 0.

Tabla3. Valores de la función con precisión =0. i xi yi 1 0 0 2 0.314159 0. 3 0.628319 0. 4 0.942478 0. 5 1.256637 0. 6 1.570796 0. 7 1.884956 0. 8 2.199115 0. 9 2.513274 0. 10 2.827433 0. 11 3.1 41593 0.

b) usando estas dos tablas como valores de una función desconocida calcúlese valores de la función sobre la malla equidistante * + usando la fórmula de interpolación de LaGrange global y compare los resultados con los valores exactos de la función ( ).

El código funciona para los valores de precisión =0.1 y =10-6,^ dichos valores se encuentras en los archivos de texto tabla_1 y tabla_2 y genera un archivo de salida en el cual se imprimen los valores de X, el valor exacto de la función Yexac y los valores al hacer la interpolación de LaGrange Ylag para cada uno de los valores de. Se procede a graficar el resultado de dichos archivos, con ayuda del programa Graph. En la figura se observa la relación entre el valor exacto de la función y la interpolación de LaGrange ( =0.1), donde se puede apreciar que el comportamiento entre dichas graficas es semejante en una buena cantidad de puntos. En fa figura 44445 representa la misma relación anterior excepto que el valor de la precisión es =10-6^ lo que hace que su comportamiento sea

aproximadamente el mismo. Se puede deducir de estas dos graficas que en general el método de interpolación de LaGrange es bueno, pero es necesario tener en cuenta el error y la precisión con la que se esté trabajando.

Figura 5. Gráfica de los valores exactos e interpolación de LaGrange para =0.

Figura 6. Gráfica de los valores exactos e interpolación de LaGrange para =10^- 6

yn=yn+Ly[i]; } return yn; } double function(double xn){ double yp; yp=exp(-xn)(sin(xn)*sin(xn)); return yp; }

c) Repitiese el cálculo del punto anterior usando las interpolaciones segmentarias lineal y parabólica y explíquese las diferencias que aparecen en estos cálculos.

Interpolación segmentaria lineal

El código lee dos archivos de texto previos (tabla_presicion_0.1 y tabla_presicion_0.000001), y genera dos archivos donde se encuentra la interpolación segmentaria lineal para cada uno de los valore de. Nuevamente se realiza la relación entre los valores de la función exacta y los de la interpolación (figura 7, 8), donde se aprecia que dicha interpolación se ajusta en buena forma al valor original, pero presenta cambios bruscos en algunos sectores.

Figura 7. Gráfica de los valores exactos e interpolación segmentaria lineal para =0.

Figura 8. Gráfica de los valores exactos e interpolación segmentaria lineal para =10^- 6

El código del programa se realizó en lenguaje C, usando el compilador Code::Blocks 13.12.

#include<stdio.h> #include<math.h> double lineal(double a,double h,double xe[],int ne,double p); int main (){ int ne=11,i,j,np=201; double pe1[ne],xe1[ne],pe2[ne],xe2[ne],x1,x2,p0=0,pf=3.141592,p,hp,d; FILE *fdat1; fdat1=fopen("tabla_presicion_0.1.txt","r"); for(i=0;i<11;i++){ fscanf(fdat1,"%lf %lf",&pe1[i],&xe1[i]); } FILE *fdat2; fdat2=fopen("tabla_presicion_0.000001.txt","r"); for(i=0;i<11;i++){ fscanf(fdat2,"%lf %lf",&pe2[i],&xe2[i]); } fclose(fdat1); fclose(fdat2); d=(pf-p0)/(ne-1); FILE *fdat3; fdat3=fopen("seg_lineal_0.1 1.txt","w"); FILE *fdat4;

  • p =0. Los resultados de las raíces.
    • 1 1. n raíz
    • 2 6.
    • 3 12.
    • 4 18.
  • p =5.
    • 1 0. n raíz
    • 2 0.
    • 3 1.
    • 4 1.
    • 5 2.
    • 6 3.
    • 7 3.
    • 8 4.
    • 9 5.
  • 10 5.
  • 11 6. - 12 6. - 13 7. - 14 8. - 15 8. - 16 9. - 17 10. - 18 10. - 19 11. - 20 11. - 21 12. - 22 13. - 23 13. - 24 14. - 25 15. - 26 15. - 27 16. - 28 16. - 29 17. - 30 18. - 31 18. - 32 19.
  • Figura 9. Gráfica de los valores exactos e interpolación segmentaria parabólica para =0.
  • Figura 10. Gráfica de los valores exactos e interpolación segmentaria parabólica para =10^-

El código del programa se realizó en lenguaje C, usando el compilador Code::Blocks 13.12.

#include<stdio.h> #include<math.h> double cuadratica(double a,double h,double xe[],int ne,double p); int main (){ int ne=11,i,j,np=201; double pe1[ne],xe1[ne],pe2[ne],xe2[ne],x1,x2,p0=0,pf=3.141592,p,hp,d; FILE *fdat1; fdat1=fopen("tabla_presicion_0.1.txt","r"); for(i=0;i<11;i++){ fscanf(fdat1,"%lf %lf",&pe1[i],&xe1[i]); } FILE *fdat2; fdat2=fopen("tabla_presicion_0.000001.txt","r"); for(i=0;i<11;i++){ fscanf(fdat2,"%lf %lf",&pe2[i],&xe2[i]); } fclose(fdat1); fclose(fdat2); d=(pf-p0)/(ne-1); FILE *fdat3; fdat3=fopen("seg_parabol_0.1 1.txt","w"); FILE fdat4; fdat4=fopen("seg_parabol_0.000001.txt","w"); hp=(pf-p0)/(np-1); for(j=0;j<=1;j++){ for(i=1;i<=np;i++){ p=p0+hp(i-1); if(j==0){ x1=cuadratica(p0,d,xe1,ne,p); fprintf(fdat3,"%9lf %15lf\n",p,x1); } if(j==1){ x2=cuadratica(p0,d,xe2,ne,p); fprintf(fdat4,"%9lf %15lf\n",p,x2); } } } fclose(fdat3); fclose(fdat4);