C++新人求教!!计算π的近似值

baidu_18434133 2015-04-20 01:47:49
计算π的近似值,π的计算公式为:

要求:精度为10-5,并输出n的大小
以下是我写的代码:
#include <iostream>
#include <cmath>
using namespace std;
float count(int max);
int main()
{
int i = 0;
float pi = 1., pi1 = 2.;
while(fabs(pi1-pi)>1.0e-5)
{
i++;
pi = count(i);
pi1 = count(i + 1);
}
cout << "n = " << i << endl;
return 0;
}
float count(int max)
{
float sum = 2.0;
for (int i = 1; i <= max; i++)
{
sum *= 4 * i * i / ((2 * i - 1)*(2 * i + 1));
}
return sum;
}

运行结果是n = 1,求解哪里错了?
...全文
2978 12 打赏 收藏 转发到动态 举报
写回复
用AI写文章
12 条回复
切换为时间正序
请发表友善的回复…
发表回复
farmliver 2015-05-03
  • 打赏
  • 举报
回复
楼上各位说的都对,类型自动转换问题。
paschen 2015-05-02
  • 打赏
  • 举报
回复
math.h 中有pi的定义: #define M_PI 3.14159265358979323846 另外精确到很多位,比如100位,可以用字符串来保存结果:

//如果要很高很高的精度,可以通过计算,以字符串来保存。
//bit为精确到小数点后的位数,datas为需要输出到的字符串的指针(datas至少要有bit+3个元素)
//最后几位可能是错的(如需准确的前n位数,可以带入n+15位去运算,最后的字符串截取至n位)。
void mult(int *a,int b,int *s,int bit);
void divi(int *a,int b,int *s,int bit);
void incr(int *a,int *b,int *s,int bit);
bool eqs(int *a,int *b,int bit);

void get_pi(int bit,char* datas)
{
	int *pi=new int[bit+1];
	int *ls=new int[bit+1];
	int *sl=new int[bit+1];
	int *p=new int[bit+1];
	for(int i=0;i<=bit;i++)
		*(pi+i)=*(ls+i)=*(sl+i)=*(p+i)=0;
	memset(pi,0,sizeof(pi));
	memset(ls,0,sizeof(ls));
	memset(sl,0,sizeof(sl));
	memset(p,0,sizeof(p));
	*pi=*ls=*sl=1;
	for(int is=1;;is++)
	{
		mult(ls,is,sl,bit);
		divi(sl,2*is+1,ls,bit);
		incr(pi,ls,p,bit);
		if(eqs(pi,p,bit))
			break;
		int *t;
		t=p;
		p=pi;
		pi=t;
	}
	mult(p,2,pi,bit);
	datas[0]=*pi+'0';
	datas[1]='.';
	for(int in=1;in<=bit;in++)
		datas[in+1]=*(pi+in)+'0';
	datas[bit+2]='\0';
	delete[] pi;
	delete[] ls;
	delete[] sl;
	delete[] p;
}

//以下4个函数是get_pi函数内调用的函数
void mult(int *a,int b,int *s,int bit)
{
	for(int i=bit,c=0;i>=0;i--)
	{
		int y=(*(a+i))*b+c;
		c=y/10;
		*(s+i)=y%10;
	}
}

void divi(int *a,int b,int *s,int bit)
{
	for(int i=0,c=0;i<=bit;i++)
	{
		int y=(*(a+i))+c*10;
		c=y%b;
		*(s+i)=y/b;
	}
}

void incr(int *a,int *b,int *s,int bit)
{
	for(int i=bit,c=0;i>=0;i--)
	{
		int y=(*(a+i))+(*(b+i))+c;
		c=y/10;
		*(s+i)=y%10;
	}
}

bool eqs(int *a,int *b,int bit)
{
	int i=0;
	while(((*(a+i))==(*(b+i)))&&(i<=bit))
		i++;
	return i>bit;
}
cao_julians 2015-05-02
  • 打赏
  • 举报
回复
现在教程中没有这个概念吗:默认类型,系统在没有明确提示时自动使用的类型,用sizeof(1)和sizeof(1.0)就能看到整型和浮点型数据的默认类型
cao_julians 2015-05-02
  • 打赏
  • 举报
回复
你用float去计算逐步求精的过程可以这样比喻,一步计算后得到了十位精度的值你马上截断为五位精度,白白浪费了。 应该知道,浮点表达式的结果是double类型的,赋值给float变量后就损失了精度,相当引入了一个误差
ForestDB 2015-04-22
  • 打赏
  • 举报
回复
随便写的。

# include <stdio.h>

int main()
{
    double old_pi = 0.0;
    double pi = 2.0;
    int i = 1;

    while (pi - old_pi > 10e-9)
    {
        old_pi = pi;
        pi = pi * 4.0 * i * i / ((2.0 * i - 1) * (2.0 * i + 1));
        i++;
    }

    printf("%i %f %f\n", i - 1, pi, old_pi);

    return 0;
}
fly_dragon_fly 2015-04-20
  • 打赏
  • 举报
回复
把整数加上小数点,这个乘不用每次从头乘到尾
百曉生 2015-04-20
  • 打赏
  • 举报
回复
int i = 0;
cout << "n = " << i << endl;
整数!!!
赵4老师 2015-04-20
  • 打赏
  • 举报
回复
仅供参考:
#include <stdio.h>
long a=10000;
long b;
long c=2800;
long d;
long e;
long f[2801];
long g;
int main() {
    for(;b-c;) f[b++]=a/5;
//  while (1) {
//      if (0==b-c) break;
//      f[b]=a/5;
//      b++;
//  }

    //f[0 - 2800] = 10000/5
    for(;d=0,g=c*2;c-=14,printf("%.4d",e+d/a),e=d%a)
          for(b=c;d+=f[b]*a,f[b]=d%--g,d/=g--,--b;d*=b);
//  while (1) {
//      d=0;
//      g=c*2;
//      if (0==g) break;
//      b=c;
//      while (1) {
//          d+=f[b]*a;
//          f[b]=d%--g;
//          d/=g--;
//          --b;
//          if (0==b) break;
//          d*=b;
//      }
//      c-=14;
//      printf("%.4d",e+d/a);
//      e=d%a;
//  }

    return 0;
}
kite289 2015-04-20
  • 打赏
  • 举报
回复
sum =sum* 4 * i * i / ((2 * i - 1)*(2 * i + 1));
highnewrain 2015-04-20
  • 打赏
  • 举报
回复
sum *= 4 * i * i / ((2 * i - 1)*(2 * i + 1));
上面代码在计算4 * i * i / ((2 * i - 1)*(2 * i + 1))这部分时是采用整数运算的,导致精度丢失 改成这样
sum *= 4 .0* i * i / ((2 * i - 1)*(2 * i + 1));
或者这样
sum =sum* 4 * i * i / ((2 * i - 1)*(2 * i + 1));
都可以
假正经的班长 2015-04-20
  • 打赏
  • 举报
回复
引用 1 楼 cjqpker 的回复:
count函数中的for语句如下写

sum *= 4.0 * i * i / ((2.0 * i - 1.0)*(2.0 * i + 1.0));
原本

sum *= 4 * i * i / ((2 * i - 1)*(2 * i + 1));
中的i是整数,所有右侧默认按照整数运算,即小数会被舍去。将数字强行加上.0后,则会按照浮点数进行运算,就正确了
同理,如下计算结果:

int a = 3, b = 4;
double c = a / b; // c=0
假正经的班长 2015-04-20
  • 打赏
  • 举报
回复
count函数中的for语句如下写

sum *= 4.0 * i * i / ((2.0 * i - 1.0)*(2.0 * i + 1.0));
原本

sum *= 4 * i * i / ((2 * i - 1)*(2 * i + 1));
中的i是整数,所有右侧默认按照整数运算,即小数会被舍去。将数字强行加上.0后,则会按照浮点数进行运算,就正确了

33,311

社区成员

发帖
与我相关
我的任务
社区描述
C/C++ 新手乐园
社区管理员
  • 新手乐园社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧