YbtOJ#752-最优分组【笛卡尔树,线段树】

正题

题目链接:http://www.ybtoj.com.cn/problem/752


题目大意

nnn个人,每个人有cic_icidid_idi分别表示这个人所在的队伍的最少/最多人数。

然后要求将这些人分成编号连续的若干队使得队伍最多,并且求分队方案数。

1≤n≤1061\leq n\leq 10^61n106


解题思路

阴间题目…

为了方便计算先定义一个结构体(包含答案和方案数)和加法运算表示取最大值/相同加方案数作为答案。

fif_ifi表示以第iii个作为末尾的答案,首先did_idi就相当于限制了一个后缀的范围,所以可以先用单调队列算出leftileft_ilefti表示根据ddd的限制从iii能选到的最左位置−1-11

然后cic_ici的限制很阴间,因为它的限制显然不是一个连续的范围。

考虑到一个l∼rl\sim rlr的转移的ccc限制只由这个区间最大的cic_ici来限制,所以可以考虑在笛卡尔树上做。这样其实加个数据结构可以轻松做到O(nlog⁡2n)O(n\log^2 n)O(nlog2n),但是这样过不了,还得优化。

分类讨论一下,我们现在考虑一个在右边的iii和一个在左边的jjj,我们已经处理好了左边的答案,要用它来更新右边的。

  1. lefti<Lleft_i<Llefti<Li<mid+cmidi< mid+c_{mid}i<mid+cmid,此时可以先不管leftleftleft了,只需要考虑后面那个,而且注意到每次iii移动一格后jjj会多一个取值位置,所以我们维护一个记录区间最优答案的线段树。然后先用线段树查询出第一个满足条件的iii的答案,然后后面每次加一个答案就好了
    然后这里一次的复杂度是左右区间的最小长度,和启发式合并类似时间复杂度O(nlog⁡n)O(n\log n)O(nlogn)
  2. lefti<Lleft_i<Llefti<Li≥mid+cmidi\geq mid+c_{mid}imid+cmid,此时对于所有的iiijjj的取值范围都是[L,mid−1][L,mid-1][L,mid1],直接拿线段树查出最大的答案,然后向右边区间修改就好了。
  3. L≤lefti<midL\leq left_i<midLlefti<mid,这个好像只能对于每个iii用线段树暴力查询。但是可以注意到,对于每个iii从头到尾只会到一次这种情况,所以时间复杂度还是O(nlog⁡n)O(n\log n)O(nlogn)
  4. lefti≥midleft_i\geq midleftimid,这个向右边分治的时候会解决,不需要这里统计

上面这四个情况的都是在一个区间里的,而且是按顺序出现的,需要注意的时候第二种情况是不能暴力枚举的,所以我们需要二分出这个情况区间的末尾

然后总共的时间复杂度就是O(nlog⁡n)O(n\log n)O(nlogn)的了,细节有点多,比如建笛卡尔树的时候还要用ststst表查区间最大之类的。


code

#pragma GCC optimize(2)
%:pragma GCC optimize(3)
%:pragma GCC optimize("Ofast")
%:pragma GCC optimize("inline")
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<queue>
#include<cctype>
#define ll long long
using namespace std;
const ll N=1e6+10,P=1e9+7,nul=-1e9+6;
struct node{ll f,g;node(ll ff=0,ll gg=0){f=ff;g=gg;return;}
};
node operator+(node x,node y){if(x.f>y.f)return node(x.f,x.g);else if(x.f<y.f)return node(y.f,y.g);return node(x.f,(x.g+y.g)%P);
}
node plu(node x)
{return node(x.f+1,x.g);}
ll read() {ll x=0,f=1; char c=getchar();while(!isdigit(c)) {if(c=='-')f=-f;c=getchar();}while(isdigit(c)) x=(x<<1)+(x<<3)+c-48,c=getchar();return x*f;
}
ll n,c[N],d[N],left[N],st[N][20],lg[N];
deque<ll > q;node f[N];
struct SegTree{node w[N<<2],lazy[N<<2];void Downdata(ll x,ll L,ll R){if(lazy[x].f==nul)return;ll mid=(L+R)>>1;w[x*2]=w[x*2]+lazy[x];w[x*2+1]=w[x*2+1]+lazy[x]; lazy[x*2]=lazy[x*2]+lazy[x];lazy[x*2+1]=lazy[x*2+1]+lazy[x];lazy[x].f=nul;return;}void Change(ll x,ll L,ll R,ll l,ll r,node p){if(l>r||l<0)return;if(L==l&&R==r){w[x]=w[x]+p;lazy[x]=lazy[x]+p;return;}ll mid=(L+R)>>1;Downdata(x,L,R);if(r<=mid)Change(x*2,L,mid,l,r,p);else if(l>mid)Change(x*2+1,mid+1,R,l,r,p);else Change(x*2,L,mid,l,mid,p),Change(x*2+1,mid+1,R,mid+1,r,p);w[x]=w[x*2]+w[x*2+1];}void Set(ll x,ll L,ll R,ll pos,node p){if(L==R){w[x]=p;return;}ll mid=(L+R)>>1;Downdata(x,L,R);if(pos<=mid)Set(x*2,L,mid,pos,p);else Set(x*2+1,mid+1,R,pos,p);w[x]=w[x*2]+w[x*2+1];}node Ask(ll x,ll L,ll R,ll l,ll r){if(l>r||l<0)return node(nul,nul);if(L==l&&R==r)return w[x];ll mid=(L+R)>>1;Downdata(x,L,R);if(r<=mid)return Ask(x*2,L,mid,l,r);if(l>mid)return Ask(x*2+1,mid+1,R,l,r);return Ask(x*2,L,mid,l,mid)+Ask(x*2+1,mid+1,R,mid+1,r);}
}T;
ll Ask(ll l,ll r){ll z=lg[r-l+1];ll x=st[l][z],y=st[r-(1<<z)+1][z];return (c[x]>=c[y])?x:y;
}
void solve(ll L,ll R){if(L==R){f[L]=f[L]+T.Ask(1,0,n,L,L);T.Set(1,0,n,L,f[L]);return;}ll x=Ask(L+1,R);solve(L,x-1);ll l=x,r=R;while(l<=r){ll mid=(l+r)>>1;if(left[mid]>=L)r=mid-1;else l=mid+1;}ll pos=r;l=max(x,L+c[x]);r=min(min(R,x+c[x]),pos);node tmp=T.Ask(1,0,n,L,l-c[x]);ll p=l-c[x]+1;for(ll i=l;i<=r;i++){f[i]=f[i]+plu(tmp);if(p<x)tmp=tmp+f[p],p++;}tmp=T.Ask(1,0,n,L,x-1);if(r+1>=x)T.Change(1,0,n,r+1,pos,plu(tmp));for(ll i=pos+1;i<=R;i++){if(left[i]>=x)break;tmp=T.Ask(1,0,n,left[i],min(i-c[x],x-1));f[i]=f[i]+plu(tmp);}solve(x,R);return;
}
signed main()
{freopen("schooldays.in","r",stdin);freopen("schooldays.out","w",stdout);n=read();for(ll i=1;i<=n;i++){c[i]=read();d[i]=read();ll &l=left[i];l=left[i-1];while(!q.empty()&&d[q.back()]>=d[i])q.pop_back();q.push_back(i);while(i-l>d[q.front()]){l++;if(q.front()==l)q.pop_front();}st[i][0]=i;}for(ll i=2;i<=n;i++)lg[i]=lg[i>>1]+1;for(ll j=1;(1<<j)<=n;j++)for(ll i=1;i+(1<<j)-1<=n;i++){ll x=st[i][j-1],y=st[i+(1<<j-1)][j-1];st[i][j]=(c[x]>=c[y])?x:y;}for(int i=0;i<(N<<2);i++)T.lazy[i]=node(nul,0),T.w[i]=node(-1e9,0);for(ll i=1;i<=n;i++)f[i]=node(nul,nul);f[0]=node(0,1);solve(0,n);if(f[n].f<=0)return 0&puts("-1");printf("%lld %lld\n",f[n].f,f[n].g);return 0;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/319392.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

牛客小白月赛 27部分题解

已做BCDEFGJ B.乐团派对 刚开始想了个贪心&#xff0c;结果不对然后直接转头想dp了。 将能力值排序。 首先我们先分出来一组&#xff0c;能力值最大的分出来一组人数是ana_nan​即下标是n−an1→nn-a_n1\to nn−an​1→n分出来一组&#xff0c;目前还剩n−ann-a_nn−an​个人…

如何向微软 Docs 和本地化社区提交翻译贡献

Docs &#xff08;docs.microsoft.com&#xff09;是微软新版的文档网站&#xff0c;重新规划了各项技术栈的文档结构&#xff0c;看起来比 MSDN 可读性更好。虽然 Docs 提供了各种语言的版本&#xff0c;但大多是机器翻译&#xff0c;某些中文文档基本读不下去。因此微软鼓励社…

【线段树】生日

题目大意 给你一个序列&#xff0c;让你进行以下操作&#xff1a; 修改一个区间的数查询区间不同数字个数 解题思路 因为数字个数很少&#xff0c;可以直接用bitset存&#xff0c;然后套线段树 code #include<bitset> #include<cstdio> #include<cstring>…

ICPC 2019-2020 North-Western Russia Regional Contest 补题部分

已做A、M&#xff0c;E和H思路已经有了没调AC 已补BEJH 最终已完成ABEJHM B - Bad Treap 大佬题解 感觉这题就很玄学。。。 #define IO ios::sync_with_stdio(false);cin.tie();cout.tie(0) #pragma GCC optimize(2) #include<set> #include<map> #include<c…

【dfs】数字

题目大意 给出x&#xff0c;问你不小于x&#xff0c;且由相同个数的4和7组成的最小的数 解题思路 对于奇数位和大于当前位数最大数的直接特判掉 对于其他的dfs枚举&#xff0c;因为如果一个位置放得比原数大&#xff0c;那么后面的都确定了&#xff0c;所以是O(n)的 code #…

【dfs】飞行棋

题目大意 给你一个n*m的网格&#xff0c;现在让你往里面填1~k&#xff08;有的位置已经填了&#xff09;&#xff0c;使其满足所有从(1,1)到(n,m)的路径不会经过相同的数字&#xff08;只能往下或往右&#xff09;&#xff0c;求方案数 解题思路 对于k<nm-1的&#xff0c;…

API测试工具SoapUI Postman对比分析

最近公司要引入API测试工具&#xff0c;经过调查和了解&#xff0c;最终决定在SoapUI 和 Postman两种工具之间做一个选择&#xff0c;两种工具在业界都很有名&#xff0c;相信很多人两种工具也都曾使用过。SoapUISoapUI是一个开源测试工具&#xff0c;通过soap/http来检查、调用…

[POI2008]STA-Station

之前都看过有换根dp&#xff0c;一直不知道是啥意思&#xff0c;本来弱弱树形dp都不太熟悉&#xff0c;不过今天工数课的时候突然想看一下&#xff0c;写个板子题练练吧。 对于我的理解&#xff0c;换根的题目一般是根不确定&#xff0c;而求得答案与根是谁有关&#xff0c;而…

Reports

试题hduoj 题意&#xff1a; 如果相邻的任意两个数相同的话&#xff0c;则输出NO&#xff0c;反之输出YES。 题解&#xff1a; 水题 我队友做的 代码&#xff1a; #include<bits/stdc.h> #define inf 1<<30 #define maxn 200000 using namespace std; int k…

【结论】分肉

题目大意 有两个数x,y&#xff0c;一轮中&#xff0c;如果x≤yx\leq yx≤y&#xff0c;那么xx,y-x&#xff0c;否则x-y,yy&#xff0c;回答经过k轮后较小的数 解题思路 可以发现xy是保持不变的&#xff0c;且x−yx2−x−y,x2>xy(x>y)x-yx\times 2-x-y,x\times 2>xy(…

在 Windows 上可以用 Docker 吗?| 洞见

简介Docker&#xff0c;或者准确一点说&#xff0c;容器技术&#xff0c;在近几年里几乎成为了应用分发和集群部署的默认技术了。背景部分&#xff0c;如果感兴趣&#xff0c;请参考闲谈集群管理模式一文。Docker 生态的成熟还有赖于其周边工具和实践模式的兴起。比如&#xff…

泰勒及洛朗展开学习笔记

2020-1024996 最近太忙了&#xff0c;今天好像没有写题&#xff0c;不过研究了一下数学hh。 2020.10.24今天又有工数课&#xff0c;我又没听&#xff0c;我记得上节工数课我看了换根dp&#xff0c;哦&#xff1f;好吧我没听过工数&#xff0c;那没事了&#xff0c;不过这次不敢…

【结论】串串串(nowcoder 20107-A)

正题 nowcoder 20107-A 题目大意 给你两个01串&#xff0c;有若干询问&#xff0c;每次询问两段长度相等的字串不同位数的奇偶性 解题思路 因为只用判断奇偶性&#xff0c;所以同时修改两个字符是不会改变结果的&#xff0c;那么可以直接将字串修改为只有0/1个1的串&#xf…

SmartSql For Asp.Net Core 最佳实践

常规操作安装 SmartSqlInstall-Package SmartSql安装 SmartSql.DIExtensionInstall-Package SmartSql.DIExtension配置SmartSqlConfig.xml写库&#xff08;Write&#xff09;必选 唯一节点读库&#xff08;Read&#xff09;可选 多节点配置PostgresqlPostgresql 客户端 NpgsqlI…

矩阵乘法学习记录

这要从校赛的一个区间与非操作题说起&#xff0c;群里大佬用的ddp思想使其满足结合律&#xff0c;但是我连矩阵乘法都不会于是从头开始学习矩阵乘法。 P3390 【模板】矩阵快速幂 和快速幂一模一样&#xff0c;只是把数乘换成矩阵乘&#xff0c;只需要定义结构体矩阵然后重载一…

51nod1600-Simple KMP【SAM,树链剖分】

正题 题目链接:http://www.51nod.com/Challenge/Problem.html#problemId1600 题目大意 给出一个字符串sss&#xff0c;每次在最后插入一个字符后求它的所有分别子串构出的failfailfail树的深度和。 1≤Q≤1051\leq Q\leq 10^51≤Q≤105 解题思路 考虑两个相等的子串长度为le…

课程 预编译框架,开发高性能应用 - 微软技术暨生态大会 2018

微软技术暨生态大会&#xff08;Tech Summit&#xff09;&#xff0c;2018 年在上海世博中心召开。这是最后一次的 Tech Summit 了&#xff1b;明年开始&#xff0c;中国大陆地区就要和其他国家和地区一样&#xff0c;进行全球 Ignite Tour 了。我也有幸成为分会场讲师团队的一…

【DP】方格计数(nowcoder 20107-B)

正题 nowcoder 20107-B 题目大意 在一个H*W的平面上&#xff0c;选择N个点&#xff08;坐标为非负整数&#xff09;&#xff0c;使得每个点之间的距离大于D&#xff0c;问你有多少种方案 解题思路 设fi,j,kf_{i,j,k}fi,j,k​为有i个格子&#xff0c;选择k个格子&#xff0c;…

YbtOJ#853-平面标记【整体二分,凸壳】

正题 题目链接:http://www.ybtoj.com.cn/contest/119/problem/3 题目大意 给出nnn个点(xi,yi)(x_i,y_i)(xi​,yi​)&#xff0c;mmm次给出(ki,ai)(k_i,a_i)(ki​,ai​)表示标记所有满足 yj>kixjaiy_j>\frac{k_i}{x_j^{a_i}}yj​>xjai​​ki​​的未标记点 求每个点…

Ocelot简易教程(五)之集成IdentityServer认证以及授权

最近比较懒&#xff08;编者注&#xff1a;作者不是真懒&#xff0c;而是在憋大招&#xff0c;他最近实现了把Ocelot的配置使用数据库存储&#xff09;&#xff0c;所以隔了N天才来继续更新第五篇Ocelot简易教程&#xff0c;本篇教程会先简单介绍下官方文档记录的内容然后在前几…