Aula Expositiva 13
4.4 Algoritmos Numéricos4.4.1 Integração por Trapézios4.4.2 Bisseção4.4.3 Série de Taylor para exp(x) e Cancelamento Catastrófico
DCC 001Programação de Computadores
2º Semestre de 2011Prof. Osvaldo Carvalho
1DCC001 - 2011 - 2
Integração por Trapézios
DCC001 - 2011 - 2 2
Integração Numérica
DCC001 - 2011 - 2 3
a bx1 x2 x3 xn+1xn
Queremos calcular A integral indefinida de é
dificilmente obtida ou não existe O primeiro passo consiste em dividir o
intervalo em n sub-intervalos iguais
dxxfb
a xf
ba,
x
Aproximações por Retângulos
Após a divisão em sub-intervalos, a área embaixo da curva pode ser aproximada por uma soma de retângulos
Temos duas formas de definição de somas: Soma de Riemann pela esquerda Soma de Riemann pela direita
DCC001 - 2011 - 2 4
Área Coberta pela Soma de Riemann pela Esquerda
DCC001 - 2011 - 2 5
O lado esquerdo de cada retângulo
coincide com a curva
xixi+1
Área = f(xi).∆x
Área Coberta pela Soma de Riemann pela Direita
DCC001 - 2011 - 2 6
O lado direito de cada retângulo coincide com a
curva
xi xi+1
Área = f(xi+1).∆x
Somas de Riemman
DCC001 - 2011 - 2 7
O lado direito de cada retângulo coincide com a
curva
O lado esquerdo de cada retângulo
coincide com a curva
Fórmulas para Somas de Riemann
DCC001 - 2011 - 2 8
n
iix
xnxxesq
xf
xfxfxfA
1
21
1
2
132n
iix
xnxxdir
xf
xfxfxfA
Função LeftRiemannSum
DCC001 - 2011 - 2 9
function lrs = LeftRiemannSum(f,a,b,n)// Soma de Riemann esquerda da função// f entre os pontos a e b com n intervalos x = linspace(a,b,n+1); delta_x = (b-a)/n; lrs = sum(f(x(1:n))) * delta_x;endfunction
Função RightRiemannSum
DCC001 - 2011 - 2 10
function rrs = RightRiemannSum(f,a,b,n)// Soma de Riemann direita da função// f entre os pontos a e b com n intervalos x = linspace(a,b,n+1); delta_x = (b-a)/n; rrs = sum(f(x(2:n+1)))* delta_x;endfunction
Somas de Riemann com 16 sub-Intervalos
DCC001 - 2011 - 2 11
Área Coberta pela Soma de Trapézios
DCC001 - 2011 - 2 12
xixi+1
Área do sub-intervalo = ∆x.(f(xi) + f(xi+1))/2
Fórmula para Aproximação por Trapézios
DCC001 - 2011 - 2 13
n
ii
xfxfx
xxfxf
xxfxf
xxfxf
xxfxf
xf
A
n
nnnn
22
2222
11
113221
Função TrapezoidalSum
DCC001 - 2011 - 2 14
function area = TrapezoidalSum(f,a,b,n)// Calcula a área sob a curva f entre a e b, // utilizando n pontos e a fórmula dos // trapézios x = linspace(a,b,n+1); delta_x = (b-a)/n; area = ( (f(x(1))+f(x(n+1)))/2 + ... sum(f(x(2:n))) ... )*delta_x;endfunction
Comparação de Convergência
DCC001 - 2011 - 2 15
n ERRO ESQUERDA ERRO DIREITA ERRO TRAPEZIO 2 4.446396327e-001 3.407585307e-001 5.194055103e-002 4 2.092337399e-001 1.834653418e-001 1.288419903e-002 8 1.013895985e-001 9.495994231e-002 3.214828114e-003 16 4.989070473e-002 4.828406570e-002 8.033195149e-004
Bisseção
DCC001 - 2011 - 2 16
Raízes de uma Função
Problema: dada uma função f, contínua, encontrar x tal que f(x) = 0
Para algumas funções, como um polinômio de 2º grau, este problema pode ser resolvido analiticamente (por uma fórmula)
Para outras não existe solução analítica, e devemos usar métodos numéricos
Ponto de partida: dois pontos a e b, tais que f(a) < 0 e f(b) > 0, ou f(a) > 0 e f(b) < 0
17DCC001 - 2011 - 2
F(a) < 0, F(b) > 0
3.0 3.5 4.0 4.5 5.0 5.5 6.0 6.5
-1.0
-0.5
0.0
0.5
1.0
1.5
ab
18DCC001 - 2011 - 2
F(a) > 0, F(b)< 0
0.0 0.5 1.0 1.5 2.0 2.5 3.0 3.5
-0.8
-0.6
-0.4
-0.2
0.0
0.2
0.4
0.6
0.8
1.0
1.2
ab
19DCC001 - 2011 - 2
Mais de uma raiz entre a e b
0 5 10 15
-0.4
-0.2
0.0
0.2
0.4
0.6
0.8
ab
20DCC001 - 2011 - 2
F(a)>0, F(b)>0 – Caso 1
0 5 10 15
-0.4
-0.2
0.0
0.2
0.4
0.6
0.8
21DCC001 - 2011 - 2
F(a)>0, F(b)>0 – Caso 2
0 5 10 15
-0.4
-0.2
0.0
0.2
0.4
0.6
0.8
22DCC001 - 2011 - 2
F(x) = 1/xF(a) < 0, F(b) > 0, mas….
-1.5 -1.0 -0.5 0.0 0.5 1.0 1.5
-6
-4
-2
0
2
4
6
f(x) = 1/x
23DCC001 - 2011 - 2
F(a).F((a+b)/2) < 0
abm = (a+b)/2
Antes, sabemos que uma raiz está aqui
Depois, sabemos que uma raiz está aqui; podemos fazer b = m
F(a)
0
F(m)
F(b)
24DCC001 - 2011 - 2
Teste simples para sinais opostos
F(b).F((a+b)/2) < 0
ab
Antes, sabemos que uma raiz está aqui
Depois, sabemos que uma raiz está aqui;
podemos fazer a = m
m = (a+b)/2
F(a)
0
F(m)
F(b)
25DCC001 - 2011 - 2
Parada do Algoritmo
A cada passo o tamanho do intervalo que contém a (uma) raiz é dividido por 2
Quando devemos parar? Cálculos numéricos sempre são
aproximados; testar se f(x) == 0 pode levar a loops infinitos
Solução: o algoritmo deve parar quando o intervalo [a,b] for suficientemente pequeno, isto é, quando b-a for menor que uma tolerância fornecida pelo usuário.
26DCC001 - 2011 - 2
A Função Bissecao Cabeçalho
function r = Bissecao(f, a, b, tol)
// se f é contínua e se f(a).f(b) < 0, esta// função calcula a raiz r com // precisão menor ou igual// ao valor de tol
endfunctionFunção da qual
se deseja conhecer uma
raiz
Intervalo que contém a
raiz
Tolerância
27DCC001 - 2011 - 2
Teste da Função Bissecao
Para testar a função Bissecao, nós precisamosDe uma função contínuaDe um intervalo onde a função troca
de sinalE de conhecer o valor de uma raiz
nesse intervalo para poder verificar o resultado 28DCC001 - 2011 - 2
A Função e^(x)sin(x)
a b
π
29DCC001 - 2011 - 2
A função exp_sin(x)
Reparem no uso de “.*”, ao invés de “*”
Isso é essencial para que a função aceite um vetor como argumento de entrada e produza um vetor como argumento de saída
function y = exp_sin(x) y = exp(-x) .* sin (x);endfunction
30DCC001 - 2011 - 2
Testando a Função Bissecao
clearexec("exp_sin.sci");exec("bissecao.sci");tolerancia = input("\nTolerância = ");while tolerancia > 0 raiz = bissecao(exp_sin,2,4, tolerancia); printf(" Raiz = %12.10f;\n Pi = %12.10f\n",raiz,%pi); tolerancia = input("\nTolerância = ");end
31DCC001 - 2011 - 2
A função BissecaoLoop
function r = bissecao(f,a,b,tol) while b-a > tol // Redução do intervalo end r = (a+b)/2;endfunction
32DCC001 - 2011 - 2
A função BissecaoRedução do Intervalo
// Redução do intervalo m = (a+b)/2; //Ponto médio if f(a)*f(m) <= 0 then // [a,m] contém uma raiz b = m; end if f(m)*f(b) <= 0 then // [m,b] contém uma raiz a = m; end
33DCC001 - 2011 - 2
Teste
Tolerância = 1.0e-3 Raiz = 3.1411132813; Pi = 3.1415926536
Tolerância = 1.0e-6 Raiz = 3.1415925026; Pi = 3.1415926536
Tolerância = 1.0e-10 Raiz = 3.1415926536; Pi = 3.1415926536
34DCC001 - 2011 - 2
Série de Taylor para exp(x) e Cancelamento Catastrófico
DCC001 - 2011 - 2 35
Série de Taylor para exp(x)
Do cálculo sabe-se que, para qualquer x, exp(x) pode ser calculado pela soma de infinitos termos
36DCC001 - 2011 - 2
Série de Taylor para exp(x)
A partir do ponto onde n >= x, n! cresce mais rapidamente que xn
Na prática a soma é feita até que o valor absoluto do termo calculado seja menor que uma tolerância desejada
37DCC001 - 2011 - 2
Função expTaylor Primeira Versão
function y = expTaylor(x,tol)// Calcula a soma dos termos // da série de Taylor até o primeiro// termo com valor absoluto menor// que a tolerância tolendfunction
38DCC001 - 2011 - 2
Testando a função expTaylor
exec("expTaylor.sci");tol = input("\ntol = ");x = input("\nx = ");while x ~= 999 expCalc = expTaylor(x,tol); printf ("\n%15g %15.8e %15.8e %15.8e\n", ... x,exp(x),expCalc,exp(x)-expCalc ) x = input("\nx = ");end Função Scilab,
muito confiável39DCC001 - 2011 - 2
Cálculo dos Termos da Série de Taylor
DCC001 - 2011 - 2 40
t0 t1 t2 t3
A Função expTaylor
function y = expTaylor(x,tol) Termo = 1; y = Termo; i = 1; while abs(Termo) >= tol Termo = Termo * x / i; y = y + Termo; i = i+1; endendfunction
41DCC001 - 2011 - 2
Teste da função expTaylorx positivo
tol = 1.0e-40x = 1 1 2.71828183e+000 2.71828183e+000 -4.44089210e-016x = 10 10 2.20264658e+004 2.20264658e+004 7.27595761e-012x = 30 30 1.06864746e+013 1.06864746e+013 -3.90625000e-003
Bons resultados para x positivo Erro 16 ordens de grandeza menor que
os valores calculados
42DCC001 - 2011 - 2
Teste da função expTaylorx negativo
tol = 1.0e-40x = -1 -1 3.67879441e-001 3.67879441e-001 -1.11022302e-016x = -10 -10 4.53999298e-005 4.53999296e-005 1.39453573e-013x = -20 -20 2.06115362e-009 5.62188447e-009 -3.56073085e-009x = -30 -30 9.35762297e-014 -3.06681236e-005 3.06681237e-005
Péssimos resultados para x negativo x=-20: erro da mesma ordem de
grandeza dos valores x=-30: valor calculado negativo!
43DCC001 - 2011 - 2
E agora?
A fórmula para a série de Taylor é provada matematicamente há (literalmente) séculos
A função exp_Taylor é uma implantação simples e direta da fórmula
O que aconteceu?44DCC001 - 2011 - 2
Origem: Aritmética de Ponto Flutuante Uso de um número fixo de bits para
representação da mantissa Aritmética de números com grandes
diferenças de ordem de grandeza não funciona como esperado:-->eps = 1.0e-23;
-->y = 1.0e23;-->x = y + eps;-->x == y ans = T
x é igual a y bit por bit!
45DCC001 - 2011 - 2
Soma de Números de Ordens de Grandeza muito Diferentes
DCC001 - 2011 - 2 46
-->eps = 1.0e-23;-->y = 1.0e23;-->x = y + eps;-->x == y ans = T
Dízimas Periódicas
0,1 = 0.00011001100110011001100…. Ou seja, 0,1 não tem representação
exata em binário
DCC001 - 2011 - 2 47
-->0.1+0.2 == 0.3 ans = F
Cancelamento Catastrófico
DCC001 - 2011 - 2 48
Precisão 6 Precisão 3 Diferença Dif/Precisão 6a 3,14159 3,14 0,00159 0,0506%b 3,13000 3,13 0,00000 0,0000%
a+b 6,27159 6,27 0,00159 0,0254%a-b 0,01159 0,01 0,00159 13,7187%
Ocorre em subtrações de números com valores absolutos próximos, sempre que se usa um número fixo de algarismos significativos, binários, decimais ou em qualquer outra base
Valores dos Termos da Série para x = -20
DCC001 - 2011 - 2 49
Valor Absoluto dos Termos da Série para x = -20
~4.3e00715 ordens de
grandeza maior que o resultado
correto
50DCC001 - 2011 - 2
Conclusões
Cuidado ao somar números de tamanhos muito diferentes e ao subtrair números de tamanhos próximos
A aritmética de ponto flutuante é melindrosa; use funções de bibliotecas sempre que possível
Por outro lado, não se deixe levar pelo pessimismo: programas numéricos funcionam como esperado na maior parte dos casos 51DCC001 - 2011 - 2
Top Related