
问题就是出在数据类型上的选用上,precision=00000001时已经超过了float的数据范围,所以导致数据截断后precision=0000000,从而程序在计算积分时可能陷入死循环,应该采用double型数据类型。其实不推荐楼主用如此多的define语句,程序的可读性和风格应该重于编程员的劳动度。。。
还有楼主对自然对数e的define也已经超过了计算机的可识别范围。。您那样精确的定义e并不会在结果上获得更加精确地结果,其实反倒会起到相反的作用,要知道与其用一个这样可能导致内存出错以及必定会导致数据截断的变量来实现精度的提高远远不如采用一个更精确的积分算法,而且c语言提供了自然数e为底的指数函数~而且貌似您的积分算法是不准确的,梯形积分的定义并非如此,其再两端的函数值应该只取1/2希望您多加细心~
如果不介意的话,就是你的precision应该改为step~这样会能更加准备的表达了这个变量的作用,在你的程序中precision变量其实是积分步长~在数值计算方法中积分精度的控制往往不是通过细化步长来表达,而是通过后一个积分值-前一个积分值<precision
这样来实现精度控制~呵呵
给你一个示例程序,也是做积分,是y=xx的[0,2]的定积分。
func(float x)
{
float f;
float a,b,c;
a=1,b=0,c=0;
f=axx+bx+c;
return f;
}
test_jifen()
{
float dx=001;
float bound_a=0,bound_b=2,x,y;
float temp;
int j;
x=bound_a;
y=0;
while(x<bound_b)
{
temp=(func(x))dx;
y+=temp;
x+=dx;
}
QMessageBox::about(this,"result","y="+QString::number(y,'g'));//这句用于输出结果
}
我用qt测试过,结果是268几,把dx的值变成0001更接近理论值266667的无限循环。
仅供参考。
#include<stdioh>
#include<mathh>
double f(double x)
{
return sqrt(4-xx);
}
main()
{
double a,b,s1,s2,s,h,m=1E-6;
int n,i;
printf("请输入积分下限a和积分上限b\n");
scanf("%lf%lf",&a,&b);
s2=0;
n=10000;
// do
{
s1=s2;
n=2n;
h=(b-a)/n;
i=1;
s2=0;
do
{
s=(f(a+ih)+f(a+(i-1)h))h/2;
s2=s2+s;
i=i+1;
}
while(i<=n);
}
// while((fabs(s1-s2))>(m(fabs(s2)-fabs(s1))));
printf("f(x)在[a,b]上的定积分为%10lf",s2);
return 0;
}
我给一楼加的注释以及修改:
#include<stdioh>
#include<mathh>
#define ARRAYBOUND 10001
void main()
{
int i = 0; //辅助变量,最常见那种
int n = 0; //将所求定积分函数曲线在x轴方向,平均分成n等分;n越大,结果越精确;不过限于此算法限制n<ARRAYBOUND,否则溢出
float x[ARRAYBOUND];//ARRAYBOUND维浮点数组,存放离散的x坐标值
float y[ARRAYBOUND];//ARRAYBOUND维浮点数组,存放每个x坐标对应的函数值;x[i],y[i]满足y[i]=f(x[i]),f是你要求定积分的函数
float x0 = 00; //定积分下限
float xn = 00; //定积分上限
float h = 00; //面积微元宽度
float J = 00; //辅助变量
/f=x^3/ //这里说明要求定积分的是函数f(x)=xxx;(y等于x的立方,x^3是vb的写法)
// printf("input x0,xn,n:");
printf("请分别输入下限(x0),上限(xn),精度(n):");
scanf("%f",&x0);
scanf("%f",&xn);
scanf("%d",&n);
h=(xn-x0)/n;//将函数图形在x方向平分成n份,h是每个面积微元的宽度
x[0]=x0; //将积分下限赋值给x[0]
for(i=0;i<=n && n<ARRAYBOUND;i++)
{
x[i]=x[0]+ih; //计算n个离散的横坐标值,存入x[]数组
y[i]=(float)pow(x[i],3);//计算n个横坐标对应的函数值,存入y[]数组。在此可以改变要求积分的函数
}
// J=00;
for(i=0;i<n;i++)
{
//J=J+y[i]+y[i+1];
J+=y[i];//将所有纵坐标值代数相加,存入J
}
//J=Jh/20;
J=Jh;//所有微元面积一次求解,因为∑hy[i]=h∑y[i];
printf("\nn=%d \n所求定积分值是: %f\n",n,J);
}
我将//J=J+y[i]+y[i+1]改为J+=y[i];将//J=Jh/20;改为J=Jh只是帮助lz理解
其实,这两种表达在理论上是等价的,不过我发现修改后,在n同样大小的情况下,结果的精度有一点点下降,还真不知为什么???
这样的话lz应该能理解了吧,其实一楼的算法还有不少值得改进的地方,希望lz能有所突破!!
以上就是关于c语言求定积分全部的内容,包括:c语言求定积分、c语言编写下面定积分计算、有关c语言用梯形法求定积分的一个程序,请帮忙修改等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!
欢迎分享,转载请注明来源:内存溢出
微信扫一扫
支付宝扫一扫
评论列表(0条)