所以我有一个程序在函数x ^ 2 + y ^ 2< 2上实现自适应2D梯形规则。 1,但似乎递归不起作用 - 这里的程序是(工作)1D梯形方法的修改形式,所以我不确定代码在哪里发生故障,它应该返回PI:
double trapezoidal(d_fp_d f,
double a, double b,
double c, double d) { //helper function
return 0.25*(b-a)*(d-c)*
(f(a, c)+f(a, d) +
f(b, c)+f(b, d));
}
double atrap( double a, double b, double c, double d, d_fp_d f, double tol )
{// helper function
return atrap1(a, b, c, d, f, tol );
}
double atrap1( double a, double b, double c, double d, d_fp_d f, double tol)
{
//implements 2D trap rule
static int level = 0;
const static int minLevel = 4;
const static int maxLevel = 30;
++level;
double m1 = (a + b)/2.0;
double m2 = (c + d)/2.0;
double coarse = trapezoidal(f,a,b,c,d);
double fine =
trapezoidal(f, a, m1, c, m2)
+ trapezoidal(f, a, m1, m2, d)
+ trapezoidal(f, m1, b, c, m2)
+ trapezoidal(f, m1, b, m2, d);
++fnEvals;
if( level< minLevel
|| ( abs( fine - coarse ) > 3.0*tol && level < maxLevel ) ){
fine = atrap1( a, m1, c, m2, f,tol/4.0)
+ atrap1( a, m1, m2, d, f, tol/4.0)
+ atrap1(m1, b, c, m2, f, tol/4.0)
+ atrap1(m1, b, m2, d, f,tol/4.0);
}
--level;
return fine;
}
其中函数由
给出double ucircle( double x, double y)
{
return x*x + y*y < 1 ? 1.0 : 0.0;
}
我的主要功能是
int main()
{
double a, b, c, d;
cout << "Enter a: " <<endl;
cin >> a;
cout << "Enter b: " <<endl;
cin >> b;
cout << "Enter c: " <<endl;
cin >> c;
cout << "Enter d: " <<endl;
cin >> d;
cout << "The approximate integral is: " << atrap( a, b, c, d, ucircle, 1.0e-5) << endl;
return 0;
}
答案 0 :(得分:1)
它实际上不会永远运行,但它实际上运行了很长时间,你认为它一直在运行,这就是原因:在第一次运行level
是一个并且函数输入你的{{1并且它自己调用了4次,现在考虑第一次:它也进入if
并再调用4次并继续...正确选择输入,就像你指定的那样,条件{{1总是if
所以只有阻止流进入abs(fine - coarse)
的内容才会true
增加然后减少,所以你的函数几乎会调用if
这真是一个很大的数字,你无法在一小时或两小时内看到它的终结!
答案 1 :(得分:0)
就像BigBoss已经写过的那样,你的程序应该完成,因为30次递归意味着4^30
atrap1
1152921504606846976
函数调用只需要很长时间,这是fabs
。只要让这个号码沉入其中。
以下是一些需要考虑的事项:
您可能希望在“中断条件”中使用abs
而不是abs
。 (我认为你应该收到整数转换的警告 - 或类似的东西 - 为此)float
可能会为double
或tol
参数返回不可预测的值。 非常高的值。
1E-11
似乎是一个表示目标精度值的变量。但是,每次递归都会进一步提高此目标精度。在第10次递归时,它已经是tol
。不确定这是有意的。无论/4.0
是什么意思。
在递归调用中,您可能不希望.0
(trapezoidal
是多余的)。
你用优化编译它,对吗?
minLevel
,maxLevel
,level
可以是宏。
由于atrap1
是静态的,您的函数不喜欢线程执行。您应该将其设为{{1}}的参数。