【JZOJ5390】逗气
来源:互联网 发布:搜索引擎优化教程 编辑:程序博客网 时间:2024/04/28 20:20
Description
Solution
这题首先把绝对值拆掉,发现它是这样一个东西:
那么我们有经典做法线段树:区间
Code
#include<cstdio>#include<cstdlib>#include<cstring>#include<algorithm>#define fo(i,j,k) for(int i=j;i<=k;i++)#define fd(i,j,k) for(int i=j;i>=k;i--)#define N 200010#define inf 10000000000000000ll#define ll long longusing namespace std;struct node{ int x,y; int wz;}w1[N],w2[N];bool cmp(node x,node y){ return x.x<y.x;}struct tree{ int l,r,o;}tr[N];struct line{ int k,b; ll f(int x){ return (ll)k*x+b; }}ln[N];int cc=1,tot=0;void pdl(int v){ if(!tr[v].l) tr[v].l=++cc;}void pdr(int v){ if(!tr[v].r) tr[v].r=++cc;}double meet(int x,int y){ return (ln[y].b-ln[x].b)*1.0/(ln[x].k-ln[y].k);}void change(int v,int l,int r,int x){ if(!tr[v].o) {tr[v].o=x;return;} int o=tr[v].o; double p=meet(x,o); int mid=(l+r)/2; if(p<=l*1.0 || p>=r*1.0 || ln[x].k==ln[o].k) { if(ln[x].f(mid)>ln[o].f(mid)) tr[v].o=x; return; } if(p<=mid*1.0) { pdl(v); if(ln[x].k>ln[o].k) tr[v].o=x,change(tr[v].l,l,mid,o); else change(tr[v].l,l,mid,x); } else { pdr(v); if(ln[x].k<ln[o].k) tr[v].o=x,change(tr[v].r,mid+1,r,o); else change(tr[v].r,mid+1,r,x); }}ll find(int v,int l,int r,int x){ if(!v) return -inf; int o=tr[v].o; if(!o) return -inf; ll tmp=ln[o].f(x); if(l==r) return tmp; int mid=(l+r)/2; if(x<=mid) return max(tmp,find(tr[v].l,l,mid,x)); else return max(tmp,find(tr[v].r,mid+1,r,x));}int lf=1;void add(int x){ ln[++tot].k=lf*w1[x].x,ln[tot].b=w1[x].y;}ll z[N];int main(){ freopen("gas.in","r",stdin); freopen("gas.out","w",stdout); int n,m; scanf("%d %d",&n,&m); int mx=0; fo(i,1,n) scanf("%d %d",&w1[i].x,&w1[i].y),mx=max(mx,max(w1[i].x,w1[i].y)); fo(i,1,m) scanf("%d %d",&w2[i].x,&w2[i].y),w2[i].wz=i,mx=max(mx,max(w2[i].x,w2[i].y)); sort(w1+1,w1+n+1,cmp),sort(w2+1,w2+m+1,cmp); int p=0; fo(i,1,m) { while(w1[p+1].x<=w2[i].x && p<n) p++,add(p),change(1,1,mx,tot); int wz=w2[i].wz; z[wz]=max(z[wz],find(1,1,mx,w2[i].y)-(ll)w2[i].x*w2[i].y); } lf=-1,p=n+1; memset(tr,0,sizeof(tr)),tot=0,cc=1; fd(i,m,1) { while(w1[p-1].x>=w2[i].x && p>1) p--,add(p),change(1,1,mx,tot); int wz=w2[i].wz; z[wz]=max(z[wz],find(1,1,mx,w2[i].y)+(ll)w2[i].x*w2[i].y); } fo(i,1,m) printf("%lld\n",z[i]);}
阅读全文
1 0
- 【JZOJ5390】逗气
- [JZOJ5390]【NOIP2017提高A组模拟9.26】逗气
- JZOJ5390. 【NOIP2017提高A组模拟9.26】逗气
- JZOJ5390. 【NOIP2017提高A组模拟9.26】逗气 单调队列
- 气
- 气
- [JZOJ5390]维护直线
- 【JZOJ 5390】【NOIP2017提高A组模拟9.26】逗气
- JZOJ 5390. 【NOIP2017提高A组模拟9.26】逗气
- 【NOIP2017提高A组模拟9.26】逗气
- 书呆子气
- 气场
- 烦气
- 气场
- 气场
- 生 气
- 气哭~~
- 一股气
- Gym 101147.A
- MySQL优化实例(详细)
- 她 she
- 初试
- she
- 【JZOJ5390】逗气
- 没有上司的晚会(树形DP)
- 位运算——强大得令人害怕
- SVM——分类与回归实例
- PAT 甲级 1097. Deduplication on a Linked List (25)
- 剑指offer之十七---包含min函数的栈
- hdu_4847_kmp_水
- HTML5-简易Canvas绘图板
- 口胡【NOIP2011DAY1】选择客栈