Codeforces 516E - Drazil and His Happy Friends(同余最短路)
首先思考一个非常简单的性质:记 \(d=\gcd(n,m)\),那么每次在一起吃完饭的男女孩编号必定与 \(d\) 同余,而根据斐蜀定理可以得到另一方面的结论:对于每一个 \(\bmod d\) 的剩余类,如果其中至少有一个男孩/女孩是快乐的,那所有与这样的男孩/女孩编号 \(\bmod d\) 同余的男孩/女孩最终都会变得快乐。
这样 \(-1\) 的情况就很好判断了:只要检查每个 \(\bmod d\) 的剩余类都至少有一个男孩/女孩是快乐的即可,特别地,如果 \(d>b+g\) 那答案肯定是 \(-1\),而显然要解决答案不是 \(-1\) 的情况,只需要对每个 \(\bmod d\) 的剩余类 \(x\) 都做一遍 \(n,m\) 的互质的情况,设其答案为 \(ans\),然后令答案对 \(ans\times d+x\) 取 \(\max\) 即可。
考虑如何解决 \(n,m\) 互质的情况,考虑同余最短路(怎么想到的/bx,实是神仙),我们考虑这样建图:
- 对于每个快乐的男孩 \(b\),连一条 \(S\to b\),权值为 \(b\) 的边。
- 对于每个快乐的女孩 \(g\),连一条 \(S\to g\bmod n\),权值为 \(g\) 的边,表示这个女孩 \(g\) 最早会在 \(g\) 时刻带动男孩 \(g\bmod n\) 变得快乐。
- 对于每个男孩 \(i\),连边 \(i\to(i+m)\bmod n\),权值为 \(m\),表示如果 \(i\) 变得快乐,那么 \(m\) 时间以后 \((i+m)\bmod n\) 也会变得快乐。
跑最短路即可,最后我们取源点到所有一开始不快乐的男孩距离的最大值,就是所有男孩变得快乐的时间的最大值,然后再对所有女孩做一遍同样的操作即可。
直接建图跑 dijkstra 复杂度是 \(n\log n\) 的,无法通过。我们发现第三类边构成了一个环,因此这个模型可以视作一个环上加了一些源点连到环上某个点的边,要求源点到所有非关键点的距离最大值,而关键点个数很小,因此我们考虑将关键点压进一个 set,然后对于两个相邻关键点 \(l,r\) 路径上的所有点,显然到源点距离最大的肯定是 \(r-1\),因此我们 \(\mathcal O(k)\) 地算出所有这样的 \(r-1\) 到源点的距离,然后取 \(\max\) 即可,这样复杂度就降到了 \(k\log k\),其中 \(k\) 为关键点个数。
#include <bits/stdc++.h>
using namespace std;
#define fi first
#define se second
#define fill0(a) memset(a,0,sizeof(a))
#define fill1(a) memset(a,-1,sizeof(a))
#define fillbig(a) memset(a,63,sizeof(a))
#define pb push_back
#define ppb pop_back
#define mp make_pair
#define mt make_tuple
#define eprintf(...) fprintf(stderr,__VA_ARGS__)
template<typename T1,typename T2> void chkmin(T1 &x,T2 y){if(x>y) x=y;}
template<typename T1,typename T2> void chkmax(T1 &x,T2 y){if(x<y) x=y;}
typedef pair<int,int> pii;
typedef long long ll;
typedef unsigned int u32;
typedef unsigned long long u64;
typedef long double ld;
namespace fastio{
#define FILE_SIZE 1<<23
char rbuf[FILE_SIZE],*p1=rbuf,*p2=rbuf,wbuf[FILE_SIZE],*p3=wbuf;
inline char getc(){return p1==p2&&(p2=(p1=rbuf)+fread(rbuf,1,FILE_SIZE,stdin),p1==p2)?-1:*p1++;}
inline void putc(char x){(*p3++=x);}
template<typename T> void read(T &x){
x=0;char c=getchar();T neg=0;
while(!isdigit(c)) neg|=!(c^'-'),c=getchar();
while(isdigit(c)) x=(x<<3)+(x<<1)+(c^48),c=getchar();
if(neg) x=(~x)+1;
}
template<typename T> void recursive_print(T x){return (!x)?void():(recursive_print(x/10),putc(x%10^48),void());}
template<typename T> void print(T x){(!x)&&(putc('0'),0);(x<0)&&(putc('-'),x=~x+1);recursive_print(x);}
template<typename T> void print(T x,char c){print(x);putc(c);}
void print_final(){fwrite(wbuf,1,p3-wbuf,stdout);}
}
const int MAXN=2e5;
const ll INFll=0x3f3f3f3f3f3f3f3fll;
int n,m,B,G,N,M;
vector<int> b[MAXN+5],g[MAXN+5];
int gcd(int x,int y){return (!y)?x:gcd(y,x%y);}
void exgcd(int x,int y,int &a,int &b){
if(!y) return a=1,b=0,void();exgcd(y,x%y,a,b);
int tmp=a;a=b;b=tmp-(x/y)*b;
}
int getinv(int a,int mod){
int x,y;exgcd(a,mod,x,y);
return (x+mod)%mod;
}
ll solve(vector<int> &b,vector<int> &g,int n,int m){
map<int,bool> in;map<int,int> dis;set<int> pos;
for(int x:b){in[x]=1;pos.insert(x);dis[x]=x;}
for(int x:g){
pos.insert(x%n);
if(!dis.count(x%n)) dis[x%n]=x%n;
else chkmin(dis[x%n],x%n);
} int iv=getinv(m,n);
vector<pair<int,pii> > vec;int pos0=(*pos.begin());
for(int p:pos) vec.pb(mp(1ll*(p-pos0)*iv%n,mp(dis[p],in[p])));
vec.pb(mp(n,mp(0,1)));sort(vec.begin(),vec.end());ll mx=-1;
// for(int i=0;i<vec.size();i++) printf("%d %d %d\n",vec[i].fi,vec[i].se.fi,vec[i].se.se);
// printf("\n");
for(int i=1;i<vec.size();i++) if(!vec[i-1].se.se||vec[i].fi!=vec[i-1].fi+1)
chkmax(mx,1ll*(vec[i].fi-vec[i-1].fi-1)*m+vec[i-1].se.fi);
// printf("%d\n",mx);
return mx;
}
int main(){
scanf("%d%d",&n,&m);int d=gcd(n,m);N=n/d;M=m/d;
if(d>MAXN) return puts("-1"),0;
scanf("%d",&B);for(int i=1,x;i<=B;i++) scanf("%d",&x),b[x%d].pb(x/d);
scanf("%d",&G);for(int i=1,x;i<=G;i++) scanf("%d",&x),g[x%d].pb(x/d);
for(int i=0;i<d;i++) if(b[i].empty()&&g[i].empty()) return puts("-1"),0;
ll res=0;
for(int i=0;i<d;i++){
chkmax(res,1ll*d*solve(b[i],g[i],N,M)+i);
chkmax(res,1ll*d*solve(g[i],b[i],M,N)+i);
} printf("%lld\n",res);
return 0;
}
Codeforces 516E - Drazil and His Happy Friends(同余最短路)的更多相关文章
- Codeforces 986F - Oppa Funcan Style Remastered(同余最短路)
Codeforces 题面传送门 & 洛谷题面传送门 感谢此题教会我一个东西叫做同余最短路(大雾 首先这个不同 \(k\) 的个数 \(\le 50\) 这个条件显然是让我们对每个 \(k\) ...
- CodeForces - 516B Drazil and Tiles(bfs)
https://vjudge.net/problem/CodeForces-516B 题意 在一个n*m图中放1*2或者2*1的长方形,问是否存在唯一的方法填满图中的‘.’ 分析 如果要有唯一的方案, ...
- CodeForces 515C. Drazil and Factorial
C. Drazil and Factorial time limit per test 2 seconds memory limit per test 256 megabytes input stan ...
- CodeForces 515B. Drazil and His Happy Friends
B. Drazil and His Happy Friends time limit per test 2 seconds memory limit per test 256 megabytes in ...
- codeforces 515C. Drazil and Factorial 解题报告
题目链接:http://codeforces.com/problemset/problem/515/C 题目意思:给出含有 n 个只有阿拉伯数字的字符串a(可能会有前导0),设定函数F(a) = 每个 ...
- codeforces 515A.Drazil and Date 解题报告
题目链接:http://codeforces.com/problemset/problem/515/A 题目意思:问能否从 (0, 0) 出发,恰好走 s 步,到达该位置(a, b). 首先容易知道, ...
- codeforces 515B. Drazil and His Happy Friends 解题报告
题目链接:http://codeforces.com/problemset/problem/515/B 题目意思:有 n 个 boy 和 m 个 girl,有 b 个 boy 和 g 个 girl ( ...
- CodeForces 516C Drazil and Park 线段树
原文链接http://www.cnblogs.com/zhouzhendong/p/8990745.html 题目传送门 - CodeForces 516C 题意 在一个环上,有$n$棵树. 给出每一 ...
- CodeForces 516B Drazil and Tiles 其他
原文链接http://www.cnblogs.com/zhouzhendong/p/8990658.html 题目传送门 - CodeForces 516B 题意 给出一个$n\times m$的矩形 ...
随机推荐
- jenkins的安装、配置使用
1.jenkins的使用 (1).需要先下载安装JDK 配置jdk的环境 变量JAVA_HOME的值是 jdk 的安装位置, 然后下载安装tomcat 安装好了之后,打开tomcat下的bin文件夹, ...
- 错误 Unresolved reference 'AF_INET' 解决办法
错误代码如下: import socketserer_socket = socket.socket(AF_INET, SOCK_DGAM) 错误信息: 原因分析: 1.AF_INET,SOCK_DGA ...
- 240.搜索二维矩阵II
从左下角位置开始搜索 时间复杂度:O(行数+列数). 想法有点像二分法,大了往一个方向找,小了往另一个方向找.由于矩阵横向和纵向都是递增,如果从(0,0)位置开始找,往右和往下都是增大,因此不知道实际 ...
- Codeforces1573B
### 问题描述 - 给你两个数组,a数组里面是1 - 2n中的奇数任意顺序排列组成,b数组里面是1 - 2n中的奇数任意顺序排列组成. - 问你最少需要多少次操作能让a的字典序小于b. ### 思路 ...
- Flink sql 之 join 与 StreamPhysicalJoinRule (源码解析)
源码分析基于flink1.14 Join是flink中最常用的操作之一,但是如果滥用的话会有很多的性能问题,了解一下Flink源码的实现原理是非常有必要的 本文的join主要是指flink sql的R ...
- Noip模拟57 2021.9.20
规律总结:联考必爆炸 T1 2A 没$A$掉的大水题,但是是真的不知道$000$前面的$00$也算先导$0$,以后要长记性,这种东西不能再错了 再打三遍: $000$前面的$00$也算先导$0$ $0 ...
- Windows平台编译器相关的几个预定义宏
WIN32 是在windows.h 中定义的宏,包含winodws.h则定义该宏 _WIN32/_WIN64跟windows平台有关的宏,_WIN32在windows 32位和64位下都有该宏,_ ...
- 必备的60个常用的Linux命令
Linux必学的60个命令Linux提供了大量的命令,利用它可以有效地完成大量的工 作,如磁盘操作.文件存取.目录操作.进程管理.文件权限设定等.所以,在Linux系统上工作离不开使用系统提供的命令. ...
- STM32核心板焊接
焊接工具和材料 电烙铁及烙铁头介绍 电烙铁有很多种,常用的有内热式.外热式.恒温式和吸锡式,为了方便携带,建议使内热式电烙铁,且要带烙铁架和海绵,烙铁架用于放置电烙铁,海绵用于擦拭烙铁锡渣,因此海绵不 ...
- 有关fgetc配合feof逐行读取文件最后一行读取两遍的错觉?
最近在做一个wifiap设置的接口,用户首先获取到当前wifi 热点的ssid 和pwd,然后修改,保存. 获取信息的时候是fopen对应的hostapd.conf文件,逐行读取,查找匹配的参数. 修 ...