此题就是个坑题, 卡精度,eps 1e-12 才可过 并且最终答案 f(left) 不可行。。 只能是 最终left right mid 中的小的值。。。
话不多说,代码
#include <vector> #include <list> #include <map> #include <set> #include <deque> #include <stack> #include <cstring> #include <bitset> #include <algorithm> #include <functional> #include <numeric> #include <utility> #include <sstream> #include <iostream> #include <iomanip> #include <cstdio> #include <cmath> #include <cstdlib> #include <ctime> #include <assert.h> #include <queue> #define REP(i,n) for(int i=0;i<n;i++) #define TR(i,x) for(typeof(x.begin()) i=x.begin();i!=x.end();i++) #define ALLL(x) x.begin(),x.end() #define SORT(x) sort(ALLL(x)) #define CLEAR(x) memset(x,0,sizeof(x)) #define FILLL(x,c) memset(x,c,sizeof(x)) using namespace std; const double eps = 1e-12; double b1, t1, b2, t2, l, ds, df,g; double f(double t,double b , double l1 ,double l2){ double vv2 = g*(l1+l2); double h = l1*l2/(l1+l2); if(h<=t && h >=b){ return sqrt(vv2); } double a = g*(l1+l2)*l1/2 - l1*l1*g/2; double vx = sqrt(a/t); double vy = g*(l1+l2)/(2*vx); double v1 = sqrt(vx*vx+vy*vy); double vx2 = sqrt(a/b); double vy2 = g*(l1+l2)/(2*vx2); double v2 = sqrt(vx2*vx2+vy2*vy2); return min(v1,v2); } double f2(double a){ return max(f(t1,b1,ds,a),f(t2,b2,l-a,df)); } void solve(){ double left = eps; double right = l; while(right - left > eps){ double lmid = (left +right)/2; double rmid = (lmid +right)/2; if(f2(lmid)>f2(rmid)){ left =lmid; }else{ right =rmid; } } double ans = min(f2(left), min(f2(right),f2((left+right)/2))); printf("%.4lf\n",ans); } int main(){ while(~scanf("%lf%lf%lf%lf%lf%lf%lf%lf",&b1, &t1, &b2, &t2, &l, &ds, &df,&g)){ solve(); } return 0; }