The 19th Zhejiang University Programming Contest - H
Princess Cjb is caught by Heltion again! Her knights Little Sub and Little Potato are going to Heltion Kingdom to rescue her.
Heltion Kingdom is composed of islands, numbered from to . There are bridges in the kingdom, among which the -th bridge connects the -th island and the -th island. The knights can go through each bridge in both directions.
Landing separately on the -th and the -th island, the two knights start their journey heading to the -th island where the princess is imprisoned. However, as the knights are fat and the bridges are unstable, there will be a risk of breaking down the bridge and falling into the water if they go through one or more common bridges during their journey.
Thus, to successfully bring back the princess, two paths \textbf{with no common bridges} are needed: one starts from the -th island and leads to the -th island, while the other starts from the -th island and also leads to the -th island.
As the princess is caught very often, the knights will ask you for help times. Each time, given their starting islands and their goal, you need to tell them whether it's possible to find two paths satisfying the constraints above.
题意
意识到首先可以进行缩点,图中所有的桥将整个图分成了数个联通快,联通块内的点之间一定有至少两条路可以相互到达。
用Tarjan求出所有的桥,缩点之后意识到整个图变成了一片森林(如果保证图联通就是一颗树),可以发现如果存在合理的路,终点所在的点一定在两个骑士的起点中间,类似
的情况,三角形是终点,当然三个点之间可以插入任意个点。
那问题就变成了判断一棵树上一个点是否在两个点中间的情况,意识到情况只有
和
两种情况(u,v为起点,标三角形的为终点),利用lca的方式判断是否满足这两种情况即可,不满足即为NO
#include <map>
#include <set>
#include <ctime>
#include <cmath>
#include <queue>
#include <stack>
#include <vector>
#include <string>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <sstream>
#include <iostream>
#include <algorithm>
#include <functional>
using namespace std;
#define For(i, x, y) for(int i=x;i<=y;i++)
#define _For(i, x, y) for(int i=x;i>=y;i--)
#define Mem(f, x) memset(f,x,sizeof(f))
#define Sca(x) scanf("%d", &x)
#define Sca2(x,y) scanf("%d%d",&x,&y)
#define Sca3(x,y,z) scanf("%d%d%d",&x,&y,&z)
#define Scl(x) scanf("%lld",&x);
#define Pri(x) printf("%d\n", x)
#define Prl(x) printf("%lld\n",x);
#define CLR(u) for(int i=0;i<=N;i++)u[i].clear();
#define LL long long
#define ULL unsigned long long
#define mp make_pair
#define PII pair<int,int>
#define PIL pair<int,long long>
#define PLL pair<long long,long long>
#define pb push_back
#define fi first
#define se second
typedef vector<int> VI;
int read(){int x = ,f = ;char c = getchar();while (c<'' || c>''){if (c == '-') f = -;c = getchar();}
while (c >= ''&&c <= ''){x = x * + c - '';c = getchar();}return x*f;}
const double eps = 1e-;
const int maxn = 2e5 + ;
const int maxm = 4e5 + ;
const int INF = 0x3f3f3f3f;
const int mod = 1e9 + ;
int N,M,K;
struct Edge{
int to,next;
bool cut;
}edge[maxm * ];
int head[maxn],tot;
const int SP = ;
int pa[maxn][SP],dep[maxn];
int scc[maxn];
vector<int>P[maxn];
int ind[maxn];
int low[maxn],dfn[maxn],Stack[maxn],Index,top;
bool Instack[maxn];
int fa[maxn],fa2[maxn];
void add(int u,int v){
edge[tot].to = v;
edge[tot].next = head[u];
edge[tot].cut = ;
head[u] = tot++;
}
void Tarjan(int u,int pre){
int v;
low[u] = dfn[u] = ++Index;
Stack[top++] = u;
Instack[u] = true;
int son = ;
int pre_cnt = ;
for(int i = head[u]; ~i; i = edge[i].next){
int v = edge[i].to;
if(v == pre && pre_cnt == ){
pre_cnt++;
continue;
}
if(!dfn[v]){
son++;
Tarjan(v,u);
if(low[u] > low[v]) low[u] = low[v];
if(low[v] > dfn[u]){
edge[i].cut = edge[i ^ ].cut = true;
}
}else if(low[u] > dfn[v]){
low[u] = dfn[v];
}
}
Instack[u] = false;
top--;
}
int find(int x){
if(x == fa[x]) return x;
return fa[x] = find(fa[x]);
}
int find2(int x){
if(x == fa2[x]) return x;
return fa2[x] = find2(fa2[x]);
}
void Union2(int a,int b){
a = find2(a); b = find2(b);
fa2[a] = b;
}
void Union(int a,int b){
a = find(a) ; b = find(b);
fa[a] = b;
}
bool vis[maxn];
void dfs(int u,int la){
pa[u][] = la; dep[u] = dep[la] + ;
for(int i = ; i < SP; i ++) pa[u][i] = pa[pa[u][i - ]][i - ];
for(int i = ; i < P[u].size(); i ++){
int v = P[u][i];
if(v == la) continue;
dfs(v,u);
}
}
int lca(int u,int v){
if(dep[u] < dep[v]) swap(u,v);
int t = dep[u] - dep[v];
for(int i = ; i < SP; i ++) if(t & ( << i)) u = pa[u][i];
for(int i = SP - ; i >= ; i --){
int uu = pa[u][i],vv = pa[v][i];
if(uu != vv){
u = uu; v = vv;
}
}
return u == v?u:pa[u][];
}
vector<PII>E;
int main(){
int T; Sca(T);
while(T--){
N = read(),M = read(),K = read();
E.clear();
for(int i = ; i <= N ; i ++){
vis[i] = low[i] = dfn[i] = Instack[i] = ;
head[i] = -;
fa2[i] = fa[i] = i;
}
Index = top = tot = ;
for(int i = ; i <= M ; i ++){
int u = read(),v = read();
add(u,v); add(v,u);
} for(int i = ; i <= N ; i ++) if(!dfn[i]) Tarjan(i,i);
for(int i = ; i <= N ; i ++){
for(int j = head[i]; ~j ; j = edge[j].next){
int v = edge[j].to;
if(!edge[j].cut) Union(i,v);
else E.pb(mp(i,v));
Union2(i,v);
}
}
int cnt = ;
for(int i = ; i <= N ; i ++){
if(fa[i] == i) scc[++cnt] = i;
}
for(int i = ; i < E.size(); i ++){
if(E[i].fi <= E[i].se) continue;
int a = find(E[i].fi),b = find(E[i].se);
if(a == b) continue;
P[a].pb(b); P[b].pb(a);
}
for(int i = ; i <= N ; i ++){
int x = find2(scc[i]);
if(!vis[x]){
vis[x] = ;
dep[scc[i]] = ;
dfs(scc[i],);
}
}
for(int i = ; i <= K; i ++){
int w = read(),u = read(),v = read();
int pw = find2(w),pu = find2(u),pv = find2(v);
if(pw != pu || pw != pv){
puts("No"); continue;
}
int fw = find(w),fu = find(u),fv = find(v);
if(dep[fu] > dep[fv]) swap(fu,fv);
if(fw == fv || fu == fw){
puts("Yes");
continue;
}
int l = lca(fu,fv);
if(lca(fv,fw) == fw && lca(fw,fu) == fu){
puts("Yes");
continue;
}
if(lca(fw,l) == l && (lca(fv,fw) == fw || lca(fu,fw) == fw)){
puts("Yes");
continue;
}
puts("No");
}
for(int i = ; i <= cnt ; i ++) P[scc[i]].clear();
}
return ;
}
The 19th Zhejiang University Programming Contest - H的更多相关文章
- The 19th Zhejiang University Programming Contest Sponsored by TuSimple (Mirror)
http://acm.zju.edu.cn/onlinejudge/showContestProblems.do?contestId=391 A Thanks, TuSimple! Time ...
- 2019 The 19th Zhejiang University Programming Contest
感想: 今天三个人的状态比昨天计院校赛的状态要好很多,然而三个人都慢热体质导致签到题wa了很多发.最后虽然跟大家题数一样(6题),然而输在罚时. 只能说,水题还是刷得少,看到签到都没灵感实在不应该. ...
- The 19th Zhejiang University Programming Contest Sponsored by TuSimple (Mirror) B"Even Number Theory"(找规律???)
传送门 题意: 给出了三个新定义: E-prime : ∀ num ∈ E,不存在两个偶数a,b,使得 num=a*b;(简言之,num的一对因子不能全为偶数) E-prime factorizati ...
- zoj 4020 The 18th Zhejiang University Programming Contest Sponsored by TuSimple - G Traffic Light(广搜)
题目链接:The 18th Zhejiang University Programming Contest Sponsored by TuSimple - G Traffic Light 题解: 题意 ...
- The 16th Zhejiang University Programming Contest-
Handshakes Time Limit: 2 Seconds Memory Limit: 65536 KB Last week, n students participated in t ...
- The 18th Zhejiang University Programming Contest Sponsored by TuSimple -C Mergeable Stack
题目链接 题意: 题意简单,就是一个简单的数据结构,对栈的模拟操作,可用链表实现,也可以用C++的模板类来实现,但是要注意不能用cin cout,卡时间!!! 代码: #include <std ...
- The 18th Zhejiang University Programming Contest Sponsored by TuSimple
Pretty Matrix Time Limit: 1 Second Memory Limit: 65536 KB DreamGrid's birthday is coming. As hi ...
- ZOJ 4016 Mergeable Stack(from The 18th Zhejiang University Programming Contest Sponsored by TuSimple)
模拟题,用链表来进行模拟 # include <stdio.h> # include <stdlib.h> typedef struct node { int num; str ...
- The 17th Zhejiang University Programming Contest Sponsored by TuSimple A
Marjar Cola Time Limit: 1 Second Memory Limit: 65536 KB Marjar Cola is on sale now! In order to ...
随机推荐
- python的学习笔记01_4基础数据类型列表 元组 字典 集合 其他其他(for,enumerate,range)
列表 定义:[]内以逗号分隔,按照索引,存放各种数据类型,每个位置代表一个元素 特性: 1.可存放多个值 2.可修改指定索引位置对应的值,可变 3.按照从左到右的顺序定义列表元素,下标从0开始顺序访问 ...
- Android RecyclerView初探
今天研究了一下RecyclerView,RecyclerView比ListView的效率更高而且可以横向滑动,所以现在许多Android项目更倾向与使用RecyclerView. 下面是一个Recyc ...
- 小米平板8.0以上系统如何不用root激活xposed框架的流程
在大多使用室的引流,或业务操作中,基本上都需要使用安卓的强大XPOSED框架,近来我们使用室购来了一批新的小米平板8.0以上系统,基本上都都是基于7.0以上系统版本,基本上都不能够刷入ROOT的su权 ...
- Java中单例模式的几种实现
目录 懒汉式单例 简单版本 synchronized版本 双重检查(Double-Check)版本 volatile 饿汉式单例 实现1 其他实现方式 静态内部类-Effective Java 枚举- ...
- Hadoop Yarn框架原理解析
在说Hadoop Yarn的原理之前,我们先来看看Yarn是怎样出现的.在古老的Hadoop1.0中,MapReduce的JobTracker负责了太多的工作,包括资源调度,管理众多的TaskTrac ...
- [20190418]exclusive latch spin count.txt
[20190418]exclusive latch spin count.txt--//昨天测试"process allocation" latch,主要这个latch与其它拴锁s ...
- MongoDB个人简单总结
当同一个变量被连续插入两次会出现id相同的异常,但是同样内容的两个变量同时插入不会有问题,可能是同一个变量同一个地址生成id相同,导致异常. 默认登陆不需要用户名密码认证,需要密码认证登陆需要在adm ...
- docker中镜像的提交和上传
本文介绍如何将本地的镜像上传到镜像仓库.以及上传时遇到"denied: requested access to the resource is denied"的解决方法. 原文地址 ...
- IDEA Can't Update No tracked branch configured for branch master or the branch doesn't exist.
IDEA Can't Update No tracked branch configured for branch master or the branch doesn't exist.To make ...
- SQL LAST() 函数
LAST() 函数 LAST() 函数返回指定的字段中最后一个记录的值. 提示:可使用 ORDER BY 语句对记录进行排序. SQL LAST() 语法 SELECT LAST(column_nam ...