bzoj1096

来源:互联网 发布:ipad监控软件 编辑:程序博客网 时间:2024/05/02 01:07

斜率优化

把原方程化开(看代码),用前缀和维护。

#include<cstdio>#include<cstdlib>#include<cstring>#include<iostream>using namespace std;long long x[1000005],p[1000005],c[1000005];long long sump[1000005],cheng[1000005];long long f[1000005];int q[1000005];long long mymin(int u1,int u2){ if (u1<u2) return u1; return u2; }double Y(int j){ return cheng[j]+f[j];  }double X(int j){ return sump[j];    }double slop(int j1,int j2){ return (Y(j1)-Y(j2))/(X(j1)-X(j2));}int main(){ int n;      scanf("%d",&n); //j~i 的人全部到i -> p[j]*(x[i]-x[j])+p[j+1]*(x[i]-x[j+1])+```+p[i-1]*(x[i]-x[i-1]) //     x[i]*(p[j]+p[j+1]+```p[i-1]) -xj*pj-x[j+1]*p[j+1]-```-x[i-1]*p[i-1]  for (int i=1;i<=n;i++) {    scanf("%lld%lld%lld",&x[i],&p[i],&c[i]);    sump[i]+=sump[i-1]+p[i];    cheng[i]+=cheng[i-1]+x[i]*p[i]; } int l=1,r=1;q[1]=0; for (int i=1;i<=n;i++) {  while(l<r&&slop(q[l],q[l+1])<=x[i])l++;  int j=q[l];  if (i==1)f[i]=c[1];  else  f[i]=f[j]+x[i]*(sump[i-1]-sump[j])-(cheng[i-1]-cheng[j])+c[i];  while(l<r&&slop(q[r],q[r-1])>slop(q[r],i))r--;  q[++r]=i; } printf("%lld\n",f[n]);}


0 0
原创粉丝点击