Toxophily Time Limit: 3000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Now given the object's coordinates, please calculate the angle between the arrow and x-axis at Bob's point. Assume that g=9.8N/m. ios
已知發射點座標爲(0,0)和重力加速度g=9.8,給出目標的座標和初速度。求能夠擊中目標的最小仰角。有兩種思路。第一種是直接若是能夠擊中目標。寫出公式,化成一元二次方程,把公式內的三角函數全部化成tan,推斷[0。PI/2]有無解;另一種方法就是三分+二分。首先三分仰角,求出軌跡在x處的縱座標最大值。若縱座標最大值小於y,則直接輸出-1,三分事後[0,r]上就是單調遞增的,直接二分就能夠。git
#include<stack>//推導公式 #include<queue> #include<cmath> #include<cstdio> #include<cstring> #include<iostream> #include<algorithm> #pragma commment(linker,"/STACK: 102400000 102400000") #define mset0(t) memset(t,0,sizeof(t)) #define lson a,b,l,mid,cur<<1 #define rson a,b,mid+1,r,cur<<1|1 using namespace std; const double PI=3.141592653; const double eps=1e-8; const int MAXN=500020; const double g=9.8; double x,y,v,ans; int main() { #ifndef ONLINE_JUDGE freopen("in.txt","r",stdin); #endif // ONLINE_JUDGE int tcase; scanf("%d",&tcase); while(tcase--) { scanf("%lf%lf%lf",&x,&y,&v); /*if(x==0||y==0) //這個if語句主要是用來特判0 50 10000這樣的數據的。但不知道爲何去掉這個也能AC { if(x==0&&y==0) printf("0.000000\n"); else if(y==0) printf("-1\n"); else if(v*v*0.5/g>=y) printf("%.6lf\n",PI/2); else printf("-1\n"); continue; }*/ ans=3; double a=g*x*x; double b=-2*v*v*x; double c=2*v*v*y+g*x*x; double der=b*b-4*a*c; if(der<0) { printf("-1\n"); continue; } double ans1=atan((-b-sqrt(der))/(2*a)); double ans2=atan((-b+sqrt(der))/(2*a)); if(ans1>=0&&ans1<=PI/2) ans=min(ans,ans1); if(ans2>=0&&ans2<=PI/2) ans=min(ans,ans2); printf("%.6lf\n",ans); } return 0; }
#include<stack>//三分+二分代碼 #include<queue> #include<cmath> #include<cstdio> #include<cstring> #include<iostream> #include<algorithm> #pragma commment(linker,"/STACK: 102400000 102400000") #define mset0(t) memset(t,0,sizeof(t)) #define lson a,b,l,mid,cur<<1 #define rson a,b,mid+1,r,cur<<1|1 using namespace std; const double PI=3.141592653; const double eps=1e-8; const int MAXN=500020; const double g=9.8; double x,y,v,ans; double geth(double r) { return (v*sin(r))*(x/(v*cos(r)))-0.5*g*(x/(v*cos(r)))*(x/(v*cos(r))); } int main() { #ifndef ONLINE_JUDGE freopen("in.txt","r",stdin); #endif // ONLINE_JUDGE int tcase; scanf("%d",&tcase); while(tcase--) { scanf("%lf%lf%lf",&x,&y,&v); if(x==0&&y==0) { printf("0.000000\n"); continue; } if(y==0) { printf("-1\n"); continue; } if(x==0) { if(v*v*0.5/g>=y) printf("%.6lf\n",PI/2); else printf("-1\n"); continue; } double l=0,r=PI/2; int cnt=10000; while(cnt--) { double mid=(l+r)/2; double mmid=(mid+r)/2; if(geth(mid)>geth(mmid)) r=mmid; else l=mid; } if(geth(r)<y) { printf("-1\n"); continue; } l=0; r=r; cnt=10000; while(cnt--) { double mid=(l+r)/2; if(geth(mid)>y) r=mid; else l=mid; } printf("%.6lf\n",r); } return 0; }