为什么在 C++ 中实现高斯勒让德算法没有产生结果?

why this implementation of a Gauss Legendre algorithm in c++ is not producing result?

我正在学习 C++,我在维基百科上找到了高斯-勒让德算法来近似 pi(link: https://en.wikipedia.org/wiki/Gauss%E2%80%93Legendre_algorithm)。 我试图用 C++ 实现它,但它没有产生任何结果。 这是代码:

#include <iostream.h>
#include <conio.h>
#include <math.h>
#include <iomanip.h>
int main()
    {
        clrscr();
        long double a0 = 1,
                b0 = 1 / sqrt(2),
                t0 = 1 / 4,
                p0 = 1,
                an, bn, pn, tn;
    int i = 0;
    while(i < 3)
    {
        an = (a0 + b0) / 2;
        bn = sqrt(a0 * b0);
        tn = t0 - (p0 * (pow((a0 - an), 2)));
        pn = 2 * p0;
        a0 = an;
        b0 = bn;
        t0 = tn;
        p0 = pn;
    }
    long double pi = (pow((an + bn), 2)) / (4 * tn);
    cout<<pi;
    getch();
    return 0;
  }

当我寻求帮助时,我找到了这个,但在我看来它是一个不同的算法 - gauss-legendre in c++

更新: 添加 i 增量程序后给出错误结果。

您没有在 while 循环中递增 i

编辑: 1. 添加行 i++; 2. 更改此代码--

while(i < 3)
{
    an = (a0 + b0) / 2;
    bn = sqrt(a0 * b0);
    tn = t0 - (p0 * (pow((a0 - an), 2)));
    pn = 2 * p0;
    a0 = an;
    b0 = bn;
    t0 = tn;
    p0 = pn;
}

--到

while(i < 3)
{
    an = (a0 + b0) / 2;
    bn = sqrt(a0 * b0);
    pn = 2 * p0;
    tn = t0 - (p0 * (pow((a0 - an), 2)));
    a0 = an;
    b0 = bn;
    t0 = tn;
    p0 = pn;
    i++;
}

将 pn 放在 tn 之上。

除了您的 while 循环变量没有更新这一事实,您还错误地声明了您的双打。声明双精度值(例如“1/4”)时,如果您懒惰,最好将它们写为“1.0/4.0”或“1/4.0”。

原因是C/C++会对整数执行“/”运算符,并在事后执行类型转换。本质上你的 t0 = 0(你可以自己检查)。

这是您的代码,经过一些修改以在每次 while 循环迭代时打印完整的双精度。

#include <iostream>
#include <cmath>
#include <limits>

int main()
{
  long double a0=1.0, b0 = 1/sqrt(2),
   t0 = 1.0/4.0, p0 = 1.0;
  long double an,bn,pn,tn;
  int i = 0;
  long double pi;
  typedef std::numeric_limits<double> dbl;
  std::cout.precision(dbl::max_digits10);
  while(i < 4)
    {
      an = (a0 + b0)/2.0;      
      bn = sqrt(a0 * b0);
      tn = t0 - (p0 * (a0-an)*(a0-an));
      pn = 2*p0;
      a0 = an,b0 = bn,p0 = pn,t0 = tn;

      pi = (an+bn)*(an+bn) / (4*tn);
      std::cout << pi << std::endl;      
      i++;
    }
  return 0;
}