math专辑
1.hdoj 3310 Volume of a cylinder
求两个圆柱相交部分的体积。
第一象限积分公式:sqrt(R * R - (r - x) * (r - x)) * sqrt(r * r - (r - x) * (r - x)); 从0积到r 。最后结果乘8。
可是不知道为什么我用龙贝格积分却错了,用分割小块就AC了,忘路过大牛指点。
分割小块:
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
using namespace std;
const int cntStep = 1000000;
double solve(double R, double r) {
double step, ans = 0;
double w, h, pos;
int i;
step = r / (cntStep * 1.0);
for(i=0; i<cntStep; ++i) {
pos = i * step + step/2;
h = sqrt(R * R - (r - pos) * (r - pos));
w = sqrt(r * r - (r - pos) * (r - pos));
ans += w * h;
}
return ans * step * 8;
}
int main() {
// freopen("c:/aaa.txt", "r", stdin);
int T;
double temp, R, r;
scanf("%d", &T);
while(T --) {
scanf("%lf %lf", &R, &r);
if(R < r) {
temp = R;
R = r;
r = temp;
}
printf("%.2lf\n", solve(R, r));
}
return 0;
}
龙贝格法:
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
using namespace std;
#define ep 0.000001 //精度限制
const int M = 100;
double ans[M][M];
double R, r;
double f(double x) {
return 4 * sqrt(R * R - (r - x) * (r - x)) * sqrt(r * r - (r - x) * (r - x));
}
double Romberg(double a,double b) { //从a积到b
double h,temp;
double v;
int i,j,k,n;
bool flag=1;
h = b - a;
ans[0][0] = h/2 * ( f(a) + f(b) );
for(i=1;i<20;++i){
for(j=0;j<=i;++j){
if(j==0) {
ans[i][0] = ans[i-1][0]/2;
n = (int)pow(2.0,i);
for(k=1,temp=0;k<=n/2;++k){
v = h/n*(2*k-1) + a;
temp+=f(v);
}
temp = temp*h/n;
ans[i][0]+=temp;
}
else{
n=(int)pow(4.0,j);
ans[i][j] = (ans[i][j-1]*n - ans[i-1][j-1])/(n-1);
}
}
temp = fabs(ans[i][i] - ans[i-1][i-1]) ;
if(temp <= ep){
return ans[i][i];
}
}
return ans[19][19];
}
int main() {
// freopen("c:/aaa.txt", "r", stdin);
int T;
double temp;
scanf("%d", &T);
while(T --) {
scanf("%lf %lf", &R, &r);
if(R < r) {
temp = R;
R = r;
r = temp;
}
printf("%.2lf\n", 2 * Romberg(0, r));
}
return 0;
}
浙公网安备 33010602011771号