Each monster in the specified environment attack and defense changes in the ratio is a fixed value, so we can treat the monster as a plane point, horizontal ordinate for attack and defense, for each monster environment as a k=-b/a of the monster line, each monster's combat effectiveness is x=0 when Y value plus y=0 x value
So we want to maintain a right upper convex shell, with a straight line card this convex shell, suppose the card to the monster is (x, y), we can use x+y-kx-y/k update the answer
For each individual monster, combat =x+y-kx-y/k, the hook function, when k=-sqrt (y/x) Gets the minimum value
Maintain a top right convex shell, for every monster on the convex hull, update the answer with a straight line of his and his last monster, and then figure out the optimal slope of the monster, and if this slope of the straight card on the convex hull of the monster is the monster then update the answer
Complexity O (n logn)
Well, if the two points are excellent, you can.
Set t=b/a
Two-point answer C, if there is a t so that for all monsters x+y+tx+y/t<=c have solution C feasible
The equation is multiplied by x at the same time, and becomes two functions, which is equivalent to the line on the axis of the intersection, each time can be O (n) judgment
Complexity O (n loginf/eps) Anyway, I'm teller.
#include <iostream> #include <cstdlib> #include <cstdio> #include <cstring> #include <cmath > #include <ctime> #include <algorithm> #include <iomanip> #include <vector> #include < stack> #include <queue> #include <map> #include <set> #include <bitset>using namespace std;# Define MAXN 1000010#define Maxm 1010#define ll long long#define INF 1000000000#define MOD 1000000007#define EPS 1e-8char x b[1<<15],*xs=xb,*xt=xb; #define GETC () (xs==xt&& (xt= (XS=XB) +fread (Xb,1,1<<15,stdin), XS==xT)? 0 :* xs++) Inline int read () {char ch=getc (); int f=1,x=0; while (!) ( ch>= ' 0 ' &&ch<= ' 9 ') {if (ch== '-') f=-1;ch=getc ();} while (ch>= ' 0 ' &&ch<= ' 9 ') {x=x*10+ (ch-' 0 '); ch=getc ();} return x*f;} struct Pt{int x;int y;pt () {}pt (int _x,int _y) {x=_x;y=_y;} Friend PT operator-(pt X,pt y) {return pt (X.X-Y.X,X.Y-Y.Y);} Friend double operator * (PT X,pt y) {return 1.0*x.x*y.y-1.0*x.y*y.x;} friend bool operator < (PT X,pt y) {Return x.x!=y.x?x.x<y.x:x.y>y.y;}}; int n;pt A[MAXN];p t s[maxn];int tp;double ans=1e10;double K (pt &x) {return-sqrt (1.0*x.y/x.x);} Double XL (PT &x,pt &y) {return x.x==y.x?-1e60:1.0* (X.Y-Y.Y)/(x.x-y.x);} Double Cal (Pt x,double k) {if (Fabs (k) <eps) {return 1e20;} return 1.0*x.x+x.y-1.0*x.x*k-1.0*x.y/k;} int main () {int i;n=read (); for (i=1;i<=n;i++) {a[i].x=read (); A[i].y=read ();} Sort (a+1,a+n+1), for (i=1;i<=n;i++) {while (tp>=2&& (S[tp]-s[tp-1]) * (A[I]-S[TP]) >0) {tp--;} S[++tp]=a[i];} Double K;if (tp!=1) {k=k (s[1]), if (K>=XL (s[1],s[2))) {Ans=min (ans,cal (S[1],k));} K=k (S[TP]), if (K<=XL (S[TP-1],S[TP])) {ans=min (ans,cal (S[tp],k));} Ans=min (Ans,cal (S[TP],XL (S[TP-1],S[TP)));} Else{ans=cal (S[1],k (s[1));} for (i=2;i<tp;i++) {k=k (s[i]), if (K<=XL (S[i-1],s[i]) &&K>=XL (s[i],s[i+1])) {ans=min (ans,cal (S[i],K ));} Ans=min (Ans,cal (S[I],XL (s[i-1],s[i)));} printf ("%.4lf\n", ans); return 0;} /**/
BZOJ4570 [Scoi2016] Monster