cf555e
cf555e(缩点)
给一个 n 个点 m 条边的图,以及 q 对点 (s,t),让你给 m 条边定向。问是否存在一种方案,使每对点的 s 能走到 t。 \(n,m,q≤ 2×10^5\).
首先,在一个边双内,一定存在一种定向方案,使得边双内点两两可达。(考虑桥)
因此,可以直接把边双缩点。然后树上差分看看有没有冲突即可。
注意rmq-st求lca用的是欧拉序!
#include <cstdio>
#include <functional>
#include <algorithm>
using namespace std;
typedef pair<int, int> pi;
#define mp make_pair
const int maxn=2e5+5;
int n, m, q;
struct Edge{
int fr, to, nxt;
}e1[maxn*2], e2[maxn*2];
int fir1[maxn], fir2[maxn], cnte1=1, cnte2=0;
void addedge(int x, int y, Edge *e, int *fir, int &cnte){
Edge &ed=e[++cnte]; ed.fr=x;
ed.to=y; ed.nxt=fir[x]; fir[x]=cnte; }
int tim, dfn[maxn], low[maxn], st[maxn], tl, cntgp, gp[maxn];
void tarjan(int u, int pe, Edge *e, int *fir){ int v;
dfn[u]=low[u]=++tim; st[++tl]=u;
for (int i=fir[u]; i; i=e[i].nxt){
v=e[i].to; if (i==pe) continue; //对于求桥只能保存父边
if (dfn[v]){ low[u]=min(low[u], dfn[v]); continue; }
tarjan(v, i^1, e, fir); low[u]=min(low[u], low[v]);
}
if (dfn[u]!=low[u]) return;
++cntgp;
while (dfn[st[tl]]!=low[st[tl]]) gp[st[tl--]]=cntgp;
gp[st[tl--]]=cntgp;
}
int block[maxn], cntb, dep[maxn], ftim[maxn], f[maxn*2][19], rt[maxn];
void st_dfs(int u, int p, Edge *e, int *fir){ int v;
block[u]=cntb; dep[u]=dep[p]+1; ftim[u]=++tim; f[tim][0]=u;
for (int i=fir[u]; i; i=e[i].nxt){
v=e[i].to; if (v==p) continue;
st_dfs(v, u, e, fir);
f[++tim][0]=u; //必须放在这里!!至于为什么,想想菊花(树)
}
}
int up[maxn], down[maxn]; //标记类型:立即生效,而不是处理后生效
int getlca(int x, int y){ //注意如果x>y要swap
x=ftim[x]; y=ftim[y];
if (x>y) swap(x, y); int c=-1;
for (int l=y-x+1; l; l>>=1) ++c;
if (dep[f[x][c]]<dep[f[y-(1<<c)+1][c]]) return f[x][c];
else return f[y-(1<<c)+1][c];
}
bool ans=true;
pi dfs(int u, int p, Edge *e, int *fir){
pi upi=mp(up[u], down[u]), tmp;
for (int i=fir[u]; i; i=e[i].nxt){
if (e[i].to==p) continue;
tmp=dfs(e[i].to, u, e, fir);
upi.first+=tmp.first; upi.second+=tmp.second;
}
if (upi.first&&upi.second) ans=false;
return upi;
}
int main(){
scanf("%d%d%d", &n, &m, &q); int x, y, lca;
for (int i=1; i<=m; ++i){
scanf("%d%d", &x, &y);
addedge(x, y, e1, fir1, cnte1);
addedge(y, x, e1, fir1, cnte1); }
for (int i=1; i<=n; ++i) if (!dfn[i]) tarjan(i, 0, e1, fir1);
int g1, g2; tim=0;
for (int i=2; i<=cnte1; ++i)
if ((g1=gp[e1[i].fr])!=(g2=gp[e1[i].to]))
addedge(g1, g2, e2, fir2, cnte2);
for (int i=1; i<=cntgp; ++i)
if (!dep[i]) ++cntb, rt[i]=1, st_dfs(i, 0, e2, fir2);
for (int i=1; i<19; ++i)
for (int j=1; j<=tim; ++j){
if (j+(1<<i-1)>tim){ f[j][i]=f[j][i-1]; continue; }
if (dep[f[j][i-1]]<dep[f[j+(1<<i-1)][i-1]])
f[j][i]=f[j][i-1]; else f[j][i]=f[j+(1<<i-1)][i-1];
}
for (int i=1; i<=q; ++i){
scanf("%d%d", &x, &y); x=gp[x]; y=gp[y]; lca=getlca(x, y);
if (block[x]!=block[y]){ puts("No"); return 0; }
up[x]+=1; up[lca]+=-1; down[y]+=1; down[lca]+=-1;
}
for (int i=1; i<=cntgp; ++i)
if (rt[i]) dfs(i, 0, e2, fir2);
puts(ans?"Yes":"No");
return 0;
}
cf555e的更多相关文章
- CF555E Case of Computer Network
题面:https://www.luogu.com.cn/problem/CF555E 题意:给定一张\(n\)个点\(m\)条边的无向图. 给定\(q\)组有向点对\((s,t)\). 询问是否存在使 ...
- 「CF555E」 Case of Computer Network
「CF555E」 Case of Computer Network 传送门 又是给边定向的题目(马上想到欧拉回路) 然而这个题没有对度数的限制,你想歪了. 然后又开始想一个类似于匈牙利的算法:我先跑, ...
- 题解 CF555E Case of Computer Network
题目传送门 题目大意 给出一个\(n\)个点\(m\)条边的无向图,有\(q\)次有向点对\((s,t)\),问是否存在一种方法定向每条边使得每个点对可以\(s\to t\). \(n,m,q\le ...
- IOI 2020 集训队作业胡扯
首先安慰自己:做的没集训队快很正常-- 很正常-- 做不完也很正常-- 很正常-- 全都不会做也很正常-- 很正常-- 表格 试题一 完成情况 试题二 完成情况 试题三 完成情况 cf549E cf6 ...
- IOI2020只因训队作业胡做
w a r n i n g ! 意 识 流 警 告 !!1 不想一个个发了,干脆直接发个合集得了qwq 感觉这辈子都做不完了\(Q\omega Q\) CF516D 写过题解了 CF505E 写过题解 ...
- IOI 2020 国家集训队作业
\(\checkmark\) 试题一 完成情况 试题二 完成情况 试题三 完成情况 cf549E cf674G arc103_f \(\checkmark\) cf594E agc034_f agc0 ...
随机推荐
- Eclipse使用总结——使用Eclipse打包带源码的jar包
平时开发中,我们喜欢将一些类打包成jar包,然后在别的项目中继续使用,不过由于看不到jar包里面的类的源码了,所以也就无法调试,要想调试,那么就只能通过关联源代码的形式,这样或多或少也有一些不方便,今 ...
- 前端学习---html基础知识
HTML基本知识 学习html首先我们先看看HTML本质: web框架本质 我们在学socket,我们创建一个socketserver,然后运行起来,有一个client客户端要连接socket服务端, ...
- 在java中RandomAccessFile类的作用:对指定文件可以进行读写的操作
- EF添加和修改
(1)//添加操作 public bool addDate() { try { //声明上下文 a_context = new AEntities(); //声明数据模型实体 //执行代码时候会先验证 ...
- 使用递归函数,输出n个元素的所有子集
题目描述: 请编写一个递归函数,用来输出n个元素的所有子集.例如,三个元素{a,b,c}的所有子集是:{},{a},{b},{c},{a,c},{ac},{b,c},{a,b,c}. 解题思路: 根据 ...
- Tensorflow学习(练习)—下载骨骼图像识别网络inception数据集
import tensorflow as tfimport osimport tarfileimport requests #inception模型下载地址inception_pretrain_mod ...
- Java c3p0 连接 MySQL
<?xml version="1.0" encoding="UTF-8"?> <!-- 需要导入c3p0驱动jar包和mysql驱动jar包 ...
- 4-fiddler抓包中文乱码:
接受到的html被压缩了,要解压,在工具栏有decode
- 14-stringstream
C++中stringstream的使用方法和样例 原创 2016年11月06日 15:46:49 标签: string / C++ 7427 之前在leetcode中进行string和int的转化时使 ...
- rosbag数据记录及转换图片、视频
博客转载自: https://blog.csdn.net/u012706484/article/details/78495896 rosbag常见的使用参数和配置 1.查看.bag中包含的信息 : r ...