Case of Computer Network

CodeForces - 555E

Andrewid the Android is a galaxy-known detective. Now he is preparing a defense against a possible attack by hackers on a major computer network.

In this network are n vertices, some pairs of vertices are connected by m undirected channels. It is planned to transfer q important messages via this network, the i-th of which must be sent from vertex si to vertex di via one or more channels, perhaps through some intermediate vertices.

To protect against attacks a special algorithm was developed. Unfortunately it can be applied only to the network containing directed channels. Therefore, as new channels can't be created, it was decided for each of the existing undirected channels to enable them to transmit data only in one of the two directions.

Your task is to determine whether it is possible so to choose the direction for each channel so that each of the q messages could be successfully transmitted.

Input

The first line contains three integers nm and q (1 ≤ n, m, q ≤ 2·105) — the number of nodes, channels and important messages.

Next m lines contain two integers each, vi and ui (1 ≤ vi, ui ≤ nvi ≠ ui), that means that between nodes vi and ui is a channel. Between a pair of nodes can exist more than one channel.

Next q lines contain two integers si and di (1 ≤ si, di ≤ nsi ≠ di) — the numbers of the nodes of the source and destination of the corresponding message.

It is not guaranteed that in it initially possible to transmit all the messages.

Output

If a solution exists, print on a single line "Yes" (without the quotes). Otherwise, print "No" (without the quotes).

Examples

Input
4 4 2
1 2
1 3
2 3
3 4
1 3
4 2
Output
Yes
Input
3 2 2
1 2
3 2
1 3
2 1
Output
No
Input
3 3 2
1 2
1 2
3 2
1 3
2 1
Output
Yes

Note

In the first sample test you can assign directions, for example, as follows: 1 → 2, 1 → 3, 3 → 2, 4 → 3. Then the path for for the first message will be 1 → 3, and for the second one — 4 → 3 → 2.

In the third sample test you can assign directions, for example, as follows: 1 → 2, 2 → 1, 2 → 3. Then the path for the first message will be 1 → 2 → 3, and for the second one — 2 → 1.

简要题意:给出一个无向图,给出q个询问S,T表示从S走到T。
问能否给这张图的边定向,使得满足q个询问

sol:因为是无向图,所以在同一个强联通分量中是两两可以随意到达,然后可以搞成一棵树,树上可以差分一下,两个数组p0,p1,S位置p0++,T位置p1++,Lca处p0--,p1--,看看是否有一个点既有p0又有p1就No了

/*
¼òÒªÌâÒ⣺¸ø³öÒ»¸öÎÞÏòͼ£¬¸ø³öq¸öѯÎÊS£¬T±íʾ´ÓS×ßµ½T¡£
ÎÊÄÜ·ñ¸øÕâÕÅͼµÄ±ß¶¨Ïò£¬Ê¹µÃÂú×ãq¸öѯÎÊ
*/
#include <bits/stdc++.h>
using namespace std;
typedef int ll;
inline ll read()
{
ll s=; bool f=; char ch=' ';
while(!isdigit(ch)) {f|=(ch=='-'); ch=getchar();}
while(isdigit(ch)) {s=(s<<)+(s<<)+(ch^); ch=getchar();}
return (f)?(-s):(s);
}
#define R(x) x=read()
inline void write(ll x)
{
if(x<) {putchar('-'); x=-x;}
if(x<) {putchar(x+''); return;}
write(x/); putchar((x%)+'');
}
#define W(x) write(x),putchar(' ')
#define Wl(x) write(x),putchar('\n')
const int N=,M=;
int n,m,Q;
int tot=,Next[M],to[M],head[N];
struct Ques{int S,T;}qq[N];
inline void Link(int x,int y)
{
Next[++tot]=head[x]; to[tot]=y; head[x]=tot;
}
int cnt=,dfn[N],low[N],top=,Sta[N],now=,Bel[N];
bool ins[N];
inline void tarjan(int x,int fat)
{
int i;
bool bo=;
dfn[x]=low[x]=++cnt; Sta[++top]=x; ins[x]=;
for(i=head[x];i;i=Next[i])
{
if(to[i]==fat&&bo) {bo=; continue;}
if(!dfn[to[i]])
{
tarjan(to[i],x); low[x]=min(low[x],low[to[i]]);
}
else if(ins[to[i]]) low[x]=min(low[x],dfn[to[i]]);
}
if(dfn[x]==low[x])
{
int oo=; now++;
while(oo!=x)
{
oo=Sta[top--]; Bel[oo]=now; ins[oo]=;
}
}
}
vector<int>E[N];
#define PB push_back
int fa[N];
inline int gf(int x)
{
return (fa[x]==x)?(x):(fa[x]=gf(fa[x]));
}
int Dep[N],ff[N][];
inline void dfs(int x,int fat)
{
int i;
for(i=;i<E[x].size();i++) if(E[x][i]!=fat)
{
Dep[E[x][i]]=Dep[x]+; ff[E[x][i]][]=x; dfs(E[x][i],x);
}
}
inline int ask_lca(int x,int y)
{
int i;
if(Dep[x]<Dep[y]) swap(x,y);
for(i=;~i;i--) if(Dep[ff[x][i]]>=Dep[y]) x=ff[x][i];
if(x==y) return x;
for(i=;~i;i--) if(ff[x][i]!=ff[y][i]) x=ff[x][i],y=ff[y][i];
return ff[x][];
}
int path[N][];
bool Vis[N];
inline void dfss(int x,int fat)
{
int i;
Vis[x]=;
for(i=;i<E[x].size();i++)
{
int V=E[x][i]; if(V==fat) continue;
dfss(V,x);
path[x][]+=path[V][]; path[x][]+=path[V][];
}
}
int main()
{
// freopen("codeforces555E.in","r",stdin);
int i,j,x,y;
R(n); R(m); R(Q);
for(i=;i<=m;i++)
{
R(x); R(y); Link(x,y); Link(y,x);
}
for(i=;i<=Q;i++) {R(qq[i].S); R(qq[i].T);}
for(i=;i<=n;i++) if(!dfn[i]) tarjan(i,);
// cout<<"now="<<now<<endl;
// for(i=1;i<=n;i++) cout<<i<<' '<<Bel[i]<<endl;
// puts("");
for(i=;i<=now;i++) fa[i]=i;
for(i=;i<=n;i++)
{
for(j=head[i];j;j=Next[j])
{
int o1=gf(Bel[i]),o2=gf(Bel[to[j]]);
if(o1==o2) continue;
E[Bel[i]].PB(Bel[to[j]]); E[Bel[to[j]]].PB(Bel[i]); fa[o1]=o2;
}
}
for(i=;i<=now;i++) if(!Dep[i]) {Dep[i]=; dfs(i,);}
// for(i=1;i<=now;i++) cout<<i<<' '<<Dep[i]<<endl;
// puts("");
for(i=;i<=;i++) for(j=;j<=now;j++) ff[j][i]=ff[ff[j][i-]][i-];
// for(i=1;i<=now;i++) cout<<i<<' '<<ff[i][0]<<endl;
// puts("");
for(i=;i<=Q;i++)
{
int S=Bel[qq[i].S],T=Bel[qq[i].T];
// cout<<S<<' '<<gf(S)<<' '<<T<<' '<<gf(T)<<endl;
if(gf(S)!=gf(T)) return puts("No"),;
int lca=ask_lca(S,T);
// cout<<S<<' '<<T<<' '<<"lca="<<lca<<endl;
path[S][]++; path[lca][]--; path[T][]++; path[lca][]--;
}
// puts("");
// for(i=1;i<=now;i++) cout<<i<<' '<<path[i][0]<<' '<<path[i][1]<<endl;
for(i=;i<=now;i++) if(!Vis[i]) dfss(i,);
for(i=;i<=Q;i++)
{
int S=Bel[qq[i].S],T=Bel[qq[i].T]; if(S==T) continue;
if((path[S][]&&path[S][])||(path[T][]&&path[T][])) return puts("No"),;
}
puts("Yes");
return ;
}
/*
Input
4 4 2
1 2
1 3
2 3
3 4
1 3
4 2
Output
Yes Input
3 2 2
1 2
3 2
1 3
2 1
Output
No Input
3 3 2
1 2
1 2
3 2
1 3
2 1
Output
Yes
*/

codeforces555E的更多相关文章

随机推荐

  1. c c++各种类型的取值范围

    int类型的变量存储值从-2147483648到2147483647 //例子 #include <iostream> using namespace std; int main(void ...

  2. php 压缩接口

    function rtnJson($obj) { if (!headers_sent() && // 如果页面头部信息还没有输出 extension_loaded("zlib ...

  3. JS 验证字符串是否能转为json格式

    var isJSON=function (str) { if (typeof str == 'string') { try { var obj = JSON.parse(str); if (typeo ...

  4. MVC授权不通过之后不执行任何自定义ActionFilter

    如下一个Action [Authorize] [F1]//自定义过滤器,继承自ActionFilter public ActionResult Index() { return View(); } 如 ...

  5. python selenium2 模拟点击+拖动 测试对象 58同城验证码

    #!/usr/bin/python # -*- coding: UTF-8 -*- # @Time : 2019/12/5 17:30 # @Author : shenghao/10347899@qq ...

  6. JS基础_实参可以是任何值

    <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title> ...

  7. CSP-S2019「Symphony」

    NOTICE:如觉得本文有什么错误或不妥之处,欢迎评论区以及私信交流,反对乱喷,如有一些让人不爽的评论或人身攻击,带来的后果本人一律不负责 准备工作 Day-inf~Day-3 000 every d ...

  8. 编写Dockerfile自定义镜像

    要求 编写一个Dockerfile自定义centos镜像,要求在容器内部可以使用vim和ifconfig命令,并且登入落脚点为/usr/local 编写Dockerfile FROM centos M ...

  9. ThreadPoolExecutor的runState和workCount变量怎么存储?

    在阅读Java线程池ThreadPoolExecutor源码的时候,发现它很巧妙地把线程池状态runState和线程数workCount两个变量存放在了一个int型变量里面. 我们先看一个数值,如下是 ...

  10. js面向对象的几种方式

    对象的字面量 var obj={}:创建实例对象 var obj=new Object();构造函数模式 function fn(){}, new fn();工厂模式:用一个函数,通过传递参数返回对象 ...