打了个set维护凸包 cdq等待填坑
#include<cstdio>
#include<cstdlib>
#include<algorithm>
#include<iostream>
#include<set>
#include<cmath>
#define dprintf(...) fprintf(stderr,__VA_ARGS__)
using namespace std;
//typedef long double ld;
typedef double ld;
inline void read(ld &x){
double a; scanf("%lf",&a); x=a;
}
const ld eps=1e-8;
inline int dcmp(ld a,ld b){
if (fabs(a-b)<eps) return 0;
return a<b?-1:1;
}
const int N=200005;
inline double sqr(int x){ return (double)x*x; }
struct Point{
ld x,y;
Point(ld x=0,ld y=0):x(x),y(y) { }
void print() const { dprintf("%.3lf %.3lf",x,y); }
friend bool operator < (Point A,Point B){ return dcmp(A.x,B.x)==0?dcmp(A.y,B.y)<0:dcmp(A.x,B.x)<0; }
friend ld operator * (Point A,Point B){ return A.x*B.y-A.y*B.x; }
friend Point operator - (Point A,Point B){ return Point(A.x-B.x,A.y-B.y); }
friend double dist(Point A,Point B){ return sqrt(sqr(A.x-B.x)+sqr(A.y-B.y)); }
};
struct Line{
Point p0,p1;
Line(Point a,Point b){
p0=a; p1=b;
}
bool operator < (const Line &B) const{
return dcmp((p1-p0)*(B.p1-B.p0),0)<0;
}
void print() const{
p0.print(); dprintf(" "); p1.print();
}
ld K()const{
return (p1.y-p0.y)/(p1.x-p0.x);
}
};
set<Point> Set;
set<Line> SetL;
typedef set<Point>::iterator ITER;
typedef set<Line>::iterator IT;
int clk;
inline void Ins(Point x){
ITER r=Set.lower_bound(x),l=r,t;
l--;
if(dcmp((*r-*l)*(x-*l),0)<0) return;
SetL.erase(Line(*l,*r));
Set.insert(x);
while (1)
{
t=r; r++;
if(r==Set.end()) break;
if(dcmp((*r-x)*(*t-x),0)>0) break;
SetL.erase(Line(*t,*r));
Set.erase(t);
}
while (1)
{
if (l==Set.begin()) break;
t=l; l--;
if(dcmp((*t-x)*(*l-x),0)>0) break;
SetL.erase(Line(*l,*t));
Set.erase(t);
}
Set.insert(x);
l=r=Set.find(x);
l--; r++;
SetL.insert(Line(*l,x));
SetL.insert(Line(x,*r));
// for (ITER i=Set.begin();i!=Set.end();i++) i->print(),dprintf("\n"); dprintf("\n");
// for (IT i=SetL.begin();i!=SetL.end();i++) i->print(),dprintf("\n"); dprintf("\n");
}
int n,S;
ld A[N],B[N],R[N];
ld f[N];
ld lim;
inline void Add(int i){
ld x=f[i]/(A[i]*R[i]+B[i]),y=R[i]*x;
Ins(Point(x,y));
}
int main()
{
scanf("%d%d",&n,&S);
for (int i=1;i<=n;i++)
read(A[i]),read(B[i]),read(R[i]);
Set.insert(Point(0,0));
Set.insert(Point(1e10,-1e20)); SetL.insert(Line(Point(0,0),Point(1e10,-1e20)));
f[1]=S; Add(1);
for (int i=2;i<=n;i++)
{
clk=i;
IT it=SetL.lower_bound( Line(Point(0,0),Point(A[i],-B[i])) );
Point ret=it->p0;
f[i]=max(f[i-1],B[i]*ret.x+A[i]*ret.y);
Add(i);
}
printf("%.3lf\n",(double)f[n]);
return 0;
}