T1.题目大意:n个人站成一排,有m个团队,每个人有且属于一个团队,可以让若干个人出队,任意交换这些人的位置后再站回去,问要让所有同一团队的人连续地站在一起,至少要出队几个。(n<=10^5,m<=20)

思路:求至少出队多少个等同于求至多有几个人可以不改变位置。假设我们确定了最后每个团队前面都站了哪些团队,显然每一队所在的区间都是确定的,考虑状压DP,f[i]表示状态为i(状态中表示已经加入了哪些团队)时最小出队人数,枚举一个团队j加入状态,对每个团队做前缀和即可知道该团队在一个区间里有多少人,即可转移,时间复杂度O(n*m+m*2^m)。

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define MM 20
#define MN 100000
int b[MN+],a[MM+],s[MM+][MN+],f[<<MM],p[<<MM];
int main()
{
int n,m,i,j;
scanf("%d%d",&n,&m);
for(i=;i<=n;++i)scanf("%d",&b[i]),++a[b[i]],s[b[i]][i]=;
for(i=;i<=m;++i)for(j=;j<=n;++j)s[i][j]+=s[i][j-];
memset(f,,sizeof(f));f[]=;
for(i=;i<<<m;++i)
{
for(j=;j<=m;++j)if(~i&(<<j-))
f[i|(<<j-)]=min(f[i|(<<j-)],f[i]+a[j]-s[j][p[i]+a[j]]+s[j][p[i]]),
p[i|(<<j-)]=p[i]+a[j];
}
printf("%d",f[(<<m)-]);
}

T2.题目大意:n个车站编号1~n,有三种车,慢车,特急车,快车,慢车走一站要时间a,特急要b,快车要c,慢车可以在任意站停,特急车只能在给定的m个车站停,现在要定k个快车站,其中必须覆盖所有特急车站,快车只能在快车站停,问从1号站出发,至多有几个站能在t时间内到达(下车、转车耗时0)。(n<=10^9,m<=k<=3000,b<c<a)

思路:先计算出不设快车站(或者说先设m个快车站覆盖特急车站)时能到达哪些站,显然要到这些站是先做特急车然后再坐一段慢车,于是我们可以算出从每个特急站下车坐慢车能到的最远的站(但要在下一个特急站之前,为了不重复统计),现在如果要新建一个快车站,自然我们应该建在某个从特急站下车后坐慢车能到的最远的站的下一个站,这样我们从特急站下车后就能直接搭上快车坐到这个站再坐慢车,我们先对每个候选的站都先算出建了这个站后能新到多少站,扔到堆里,每次我们取出最大的建,建了这个站后我们得到一种新的选择,就是在这个快车站下车后坐慢车能到的站的后一个站再建一个快车站,我们重新算一遍再扔回堆里即可。总复杂度O(klogk),实际上不用堆打个暴力找最大也能过嘛。

#include<cstdio>
#include<algorithm>
#include<queue>
using namespace std;
#define ll long long
#define MN 3000
#define mp(x,y) make_pair(x,y)
int a,b,c,s[MN+],r[MN+];ll t;
priority_queue<pair<int,int> > pq;
void push(int x)
{
ll v=t-(ll)s[x]*b-(ll)(r[x]-s[x])*c;
if(v<){pq.push(mp(,x));return;}
int cp=r[x];
r[x]=min(r[x]+v/a+,(ll)s[x+]);
pq.push(mp(r[x]-cp,x));
}
int main()
{
int n,m,k,i,ans=;
scanf("%d%d%d%d%d%d%lld",&n,&m,&k,&a,&b,&c,&t);
for(i=;i<=m;++i)scanf("%d",&s[i]),--s[i];s[i]=n;
for(i=;i<=m;++i)
{
if((ll)s[i]*b>t)break;
r[i]=min(s[i]+(t-(ll)s[i]*b)/a+,(ll)s[i+]);
ans+=r[i]-s[i];
push(i);
}
for(i=k-m;i--;)
{
ans+=pq.top().first;
push(pq.top().second);
pq.pop();
}
printf("%d",ans-);
}

T3.没有这题

T4.题目大意:某派对搞了两个n个团队的人气排行榜,排行榜上有两个值,分别为排名第几的团队的所属学校和人气值,但第二个榜的报道出了点偏差,有几个学校写错了,有两个条件:一个团队的学校不会改变;由于第二个榜在第一个榜之后出,同一团队在第二个榜的人气不会低于在第一个榜的人气。现在问至少改几个第二个榜的学校才能让信息合法。(n<=200,000)

思路:我们让第一个榜和第二个榜的团队一一对应来建立二分图匹配模型,第一个榜的一个排名和第二个榜的一个排名能匹配当且仅当第二个榜的这个排名的人气不小于第一个榜的人气,且若这两个排名的学校相同,花费为0,否则花费为1,然后我们就能建出一个边数为O(n^2)的费用流图,大概能拿30分。把这个图优化到O(n)就能拿70分,优化思路是这样的:把第二个榜的每个点拆成两个点,分别表示与相同学校的匹配和任意学校匹配,然后再建一个点限制这两个点的流量,之后第一个榜的每个点分别向能匹配到的最小的任意学校点连费用1,向能匹配到的最小的相同学校连费用0,第二个榜的所有点再从小往大连流量INF费用0,图就建完了。但我们显然还是过不了200,000。其实这个匹配过程不用建图优化,是可以直接贪心解决的,每次找到最小的第二个榜的点向前匹配,如果我们找到了与它相同学校的点,显然直接匹配最优(因为此时不大于它的所有点向后能连的边是相同的),如果没有找到,我们只好选一个不同学校的匹配,但我们一时无法抉择选出哪个,就先记下在这之后要为它留下一个点匹配,我们用线段树维护每个未能直接匹配到的第二个榜的点,不大于它的点至多还能取几个,每次要找匹配点时,找到最大的不大于它的第一个榜的点,计算区间最小值看看会不会与前面冲突,不冲突就匹配并区间-1。总复杂度O(nlogn)。

#include<cstdio>
#include<algorithm>
#include<vector>
using namespace std;
inline int read()
{
int x;char c;
while((c=getchar())<''||c>'');
for(x=c-'';(c=getchar())>=''&&c<='';)x=(x<<)+(x<<)+c-'';
return x;
}
#define MN 200000
#define INF 0x7FFFFFFF
#define L (k<<1)
#define R (k<<1|1)
struct team{int t,p,x;}p[MN*+];
bool cmp(team a,team b){return a.p==b.p?a.x>b.x:a.p<b.p;}
vector<int> q[MN+];
struct node{int l,r,mn,mk;}t[MN*+];
int b[MN+],bn;
inline void up(int k){t[k].mn=min(t[L].mn,t[R].mn);}
inline void mark(int k,int x){t[k].mn+=x;t[k].mk+=x;}
inline void down(int k){t[k].mk?(mark(L,t[k].mk),mark(R,t[k].mk),t[k].mk=):;}
void build(int k,int l,int r)
{
t[k].mn=INF;
if((t[k].l=l)==(t[k].r=r))return;
int mid=l+r>>;
build(L,l,mid);build(R,mid+,r);
}
int query(int k,int l,int r)
{
if(t[k].l==l&&t[k].r==r)return t[k].mn;
down(k);
int mid=t[k].l+t[k].r>>;
if(r<=mid)return query(L,l,r);
if(l>mid)return query(R,l,r);
return min(query(L,l,mid),query(R,mid+,r));
}
void change(int k,int x,int z)
{
if(t[k].l==t[k].r){t[k].mn=z;return;}
down(k);
change(x>t[k].l+t[k].r>>?R:L,x,z);
up(k);
}
void dec(int k,int l,int r)
{
if(t[k].l==l&&t[k].r==r){mark(k,-);return;}
down(k);
int mid=t[k].l+t[k].r>>;
if(r<=mid)dec(L,l,r);
else if(l>mid)dec(R,l,r);
else dec(L,l,mid),dec(R,mid+,r);
up(k);
}
int main()
{
int n=read(),i,s=,x,ans=;
for(i=;i<n;++i)p[i].t=read(),p[i].p=read(),p[i].x=;
for(i=;i<n;++i)p[i+n].t=read(),p[i+n].p=read();
build(,,n);n<<=;sort(p,p+n,cmp);
for(i=;i<n;++i)
if(p[i].x)q[p[i].t].push_back(p[i].p),++s;
else
if(!q[p[i].t].empty())
{
x=lower_bound(b+,b+bn+,q[p[i].t][q[p[i].t].size()-])-b;
if(x>bn||query(,x,bn))q[p[i].t].pop_back(),--s,x<=bn?(dec(,x,bn),):;
else b[++bn]=p[i].p,change(,bn,s-bn),++ans;
}
else b[++bn]=p[i].p,change(,bn,s-bn),++ans;
printf("%d",ans);
}

洛谷4月月赛R1的更多相关文章

  1. 洛谷3月月赛 R1 Step! ZERO to ONE

    洛谷3月月赛 R1 Step! ZERO to ONE 普及组难度 290.25/310滚粗 t1 10分的日语翻译题....太难了不会... t2 真·普及组.略 注意长为1的情况 #include ...

  2. 洛谷4月月赛R1 Happy Poppin' Party Train

    来自FallDream的博客,未经允许,请勿转载,谢谢. 听学长说的就来玩一玩,随便乱打打  没想到一堆人被取消了成绩,莫名混了个Rank3 还有第一题数据肯定是有问题 --------------- ...

  3. 洛谷4月月赛R2

    洛谷4月月赛R2 打酱油... A.koishi的数学题  线性筛约数和就可以\(O(N)\)了... #include <iostream> #include <cstdio> ...

  4. 【洛谷5月月赛】玩游戏(NTT,生成函数)

    [洛谷5月月赛]玩游戏(NTT,生成函数) 题面 Luogu 题解 看一下要求的是什么东西 \((a_x+b_y)^i\)的期望.期望显然是所有答案和的平均数. 所以求出所有的答案就在乘一个逆元就好了 ...

  5. 【LGR-054】洛谷10月月赛II

    [LGR-054]洛谷10月月赛II luogu 成功咕掉Codeforces Round #517的后果就是,我\(\mbox{T4}\)依旧没有写出来.\(\mbox{GG}\) . 浏览器 \( ...

  6. 【LGR-051】洛谷9月月赛

    [LGR-051]洛谷9月月赛 luogu 签到题 description 给出\(K\)和质数\(m\),求最小的\(N\)使得\(111....1\)(\(N\)个\(1\))\(\equiv k ...

  7. 「LGR-049」洛谷7月月赛 D.Beautiful Pair

    「LGR-049」洛谷7月月赛 D.Beautiful Pair 题目大意 : 给出长度为 \(n\) 的序列,求满足 \(i \leq j\) 且 $a_i \times a_j \leq \max ...

  8. 洛谷9月月赛round2

    洛谷9月月赛2 t1 题意:懒得说了 分析:模拟 代码: program flag; var a:..,..]of char; n,i,m,j,x,y,ans,k:longint; begin ass ...

  9. 「P4996」「洛谷11月月赛」 咕咕咕(数论

    题目描述 小 F 是一个能鸽善鹉的同学,他经常把事情拖到最后一天才去做,导致他的某些日子总是非常匆忙. 比如,时间回溯到了 2018 年 11 月 3 日.小 F 望着自己的任务清单: 看 iG 夺冠 ...

随机推荐

  1. 网络1712--c语言字符数组作业总结..

    ---恢复内容开始--- 作业亮点 1.总体情况 1.大部分同学利用了流程图后,对于思路的理解有了提升. 2.很多同学在总结方面写的很不错,能够罗列问题贴出解决问题,我们能够看到你们的进步 2.作业发 ...

  2. 每日冲刺报告——Day1(Java-Team)

    第一天报告(11.2  周四) 团队:Java-Team 成员: 章辉宇(284) 吴政楠(286) 陈阳(PM:288) 韩华颂(142) 胡志权(143) github地址:https://git ...

  3. Beta开始前准备

    Beta准备 1. 讨论组长是否重选的议题和结论. 经过讨论,我们认为,经过一段时间的磨合,现任组长是不需要更换的. 2. 下一阶段需要改进完善的功能. 增加关于征信的功能,贴近选题主题 美化界面,尽 ...

  4. 201621123068 Week03-面向对象入门

    1. 本周学习总结 初学面向对象,会学习到很多碎片化的概念与知识.尝试学会使用思维导图将这些碎片化的概念.知识点组织起来.请使用工具画出本周学习到的知识点及知识点之间的联系.步骤如下: 1.1 写出你 ...

  5. pandas 数据分析使用

    https://github.com/Erick-LONG/data_analysis/blob/master/%E6%95%B0%E6%8D%AE%E5%88%86%E6%9E%90%20%E9%8 ...

  6. 十、Python练习----基础搭建飞机大战

    只是简单的学习了pygame,实现飞机的摧毁还需要多张图片的切换,和sprite(碰撞精灵),还有多种音效的添加(如背景音乐.摧毁特效).以后再深入学习我只是练习一下python. 一.搭建界面(基于 ...

  7. SQLite 带你入门

    SQLite数据库相较于我们常用的Mysql,Oracle而言,实在是轻量得不行(最低只占几百K的内存).平时开发或生产环境中使用各种类型的数据库,可能都需要先安装数据库服务(server),然后才能 ...

  8. js实现图片(高度不确定)懒加载

    最近一直在弄广告页,由于广告页几乎都是图片拼凑起来的,为了减少服务器压力和带宽,采用图片懒加载方式,但是我们的图片高度又不确定,所以我在网上下载了echo.js自己改了一下. 大体思路是:让首页先加载 ...

  9. 阿里云API网关(7)开发指南-API参考

    网关指南: https://help.aliyun.com/document_detail/29487.html?spm=5176.doc48835.6.550.23Oqbl 网关控制台: https ...

  10. jQuery ajax方法success()中后台传来的四种数据类型

    1.后台返回一个页面 js代码 /**(1)用$("#content-wrapper").html(data);显示页面*/ $.ajax({ async : false, cac ...