2017-01-21 82 views
-1

我正在一些簡單的東西...我想,但有一些讓我困擾。餘弦泰勒aproximation C語言

double x,t,cos_aprox,eps; 
int k; 
t=1.0; 
k=1; 
cos_aprox=1.0;` 

printf("Introduceti x pentru care se calculeaza cos(x) si eroarea epsilon:\n"); 
if(scanf("%lf%lf",&x,&eps)!=2) 
{ 
    printf("Date eronate!!\n"); 
    exit(1); 
} 
else 
{ 
    do 
    { 
     t=t*(-1)*x*x/(k*(k+1)); 
     cos_aprox+=t; 
     k+=2; 

    } 
    while(fabs(t)>eps); 

    printf("Valoarea aproximativa a lui cos(%g) este %.9g. k este %d\n",x,cos_aprox,k); 
    printf("Valoarea lui cos(%g), folosind functia din biblioteca, este %.9g.",x,cos(x)); 
} 

它返回了良好的效果,但是當我選擇了39個弧度的任意值有它,庫函數cos(x)之間的顯著差異。

任何猜測?

+2

只有當參數在'[-pi/4,pi/4]'範圍內時纔有效。您需要用大整數數學來表示縮小所需的pi數位數。文章:http://citeseer.ist.psu.edu/viewdoc/summary?doi=10.1.1.67.5616 – deamentiaemundi

+0

在while循環之前使用'x = fmod(x,2 * pi);'來改進。這對大'x'像'x> 1e10'仍然有問題。如何使用你自己的代碼精確地在很大範圍內工作'cos()'的細節不是「容易」 – chux

回答

1

OP對泰勒級數的使用受到數值限制,其值爲x。大交替符號術語的加入累積了太多的誤差。修改代碼以查看這些條款。

t = t*(-1)*x*x/(k*(k+1)); 
printf("%e\n", t); 

兩個正弦和餘弦計算益處參數減少到 範圍[-2π... +2π]。以下是良好的第一步,並將提供更大範圍內減少x的錯誤。

x = fmod(x, 2*π); 

進一步降低到範圍[0 ... +π/ 4]可以使用通常的三角恆等式和remquo()被採用。 Degrees example


麻煩的是,上面的計算依賴於π的近似值。 π是無理數,不能完全表示爲double。所有有限數double都是有理數。所以使用機器pi

// example 
#define M_PI 3.1415926535897932384626433832795 
x = fmod(x, M_PI); 

爲了實現在整個範圍精確計算的double x需要複雜的擴展精度的技術。搜索爭論減少的巨大論據:好到最後一位