洛谷 P3209 [HNOI2010] 平面图判定
链接:
题意:
给出 \(T\) 张无向图 \((T\leq100)\),并给出它对应的哈密顿回路,判断每张图是否是平面图。
分析:
平面图判定问题貌似是有线性做法的,这里给出链接,不是本题解重点。
在想不到上述算法的情况下,我们发现题目给出了该图的哈密顿回路,所以我们把无向图按哈密顿回路排成一个环。此时不在环上的边之间才可能出现交叉,所以我们考虑暴力 \(O(m^2)\) 枚举,对于可能产生交叉的两条边,只有他们在环的两侧时才不会相交,所以当 \(a,b\) 两条边可能相交时, \(a\) 在内侧则 \(b\) 一定在外侧。发现了 2-sat 模型。
算法:
简单说下算法,先找到所有不在环上的边。\(O(m^2)\) 暴力枚举,判断每两条边是否可能相交,如果可能相交,那么在 2-sat 中
insert(i,j+tot);
insert(i+tot,j);
insert(j,i+tot);
insert(j+tot,i);
最后 tarjan 求强连通分量,\(O(m+m^2)\)。
总复杂度 \(O(m^2)\)。
优化:
显然 \(O(m^2)\) 的复杂度无法通过 \(M\leq10000\) 的数据,但学过平面图的我们发现可以利用平面图的性质将 \(m\) 优化至 \(n\) 的范围。
有
设G是一个面数为 f 的(n,m)连通简单平面图且n≥3,则m≤3n-6
我们可以特判 \(m\) 将 \(m\) 缩小到 \(3n-6\) 范围内,那么 \(O(n^2)\) 的时间复杂度就可以随便过了。
代码:
#include<bits/stdc++.h>
using namespace std;
#define in read()
inline int read(){
int p=0,f=1;
char c=getchar();
while(c>'9'||c<'0'){if(c=='-')f=-1;c=getchar();}
while(c>='0'&&c<='9'){p=p*10+c-'0';c=getchar();}
return p*f;
}
const int N=1205;
const int M=360005;
int ed[N],tot;
struct edge{
int v,next;
}e[M];
int head[N],en;
void insert(int u,int v){
e[++en].v=v;
e[en].next=head[u];
head[u]=en;
}
int n,m;
int sta[N],low[N],dfn[N],id[N],sum,sign,top;
bool vis[N];
void dfs(int u){
low[u]=dfn[u]=++sign;
vis[u]=true;sta[++top]=u;
for(int i=head[u];i;i=e[i].next){
int v=e[i].v;
if(!dfn[v]) dfs(v),low[u]=min(low[u],low[v]);
else if(vis[v]) low[u]=min(low[u],dfn[v]);
}
if(low[u]==dfn[u]){
sum++;int i=sta[top--];
while(i!=u){
vis[i]=false;
id[i]=sum;
i=sta[top--];
}
vis[i]=false;
id[i]=sum;
}
}
int q[205];
int p[205];
bool check(){
for(int i=1;i<=tot;i++)
if(id[i]==id[i+tot])
return false;
return true;
}
struct QWQ{
int a,b;
}a[10005];
void clean(){
memset(head,0,sizeof(head));
memset(dfn,0,sizeof(dfn));
memset(low,0,sizeof(low));
memset(sta,0,sizeof(sta));
memset(id,0,sizeof(id));
sum=sign=en=tot=top=0;
}
inline int cinab(int a,int b,int c){
return (c>a&&c<b)?1:0;
}
signed main(){
int T=in;
while(T--){
clean();
n=in,m=in;
for(int i=1;i<=m;i++)
a[i].a=in,a[i].b=in;
for(int i=1;i<=n;i++){
q[i]=in;
p[q[i]]=i;
//p[i] 是 i 在环上的次序
}
if(m>3*n-6){
cout<<"NO"<<'\n';
continue;
}
for(int i=1;i<=m;i++){
a[i].a=p[a[i].a],a[i].b=p[a[i].b];
if(a[i].a>a[i].b)
swap(a[i].a,a[i].b);
if(a[i].b-a[i].a!=1&&a[i].b-a[i].a!=n-1)
ed[++tot]=i;
}
for(int i=1;i<tot;i++)
for(int j=i+1;j<=tot;j++){
int xa=a[ed[i]].a,xb=a[ed[i]].b,ya=a[ed[j]].a,yb=a[ed[j]].b;
//我们用一个端点在第一条线内而另一个端点不在来判断,需要特判端点相同的情况
if(xa==ya||xa==yb||xb==ya||xb==yb)continue;
if(cinab(xa,xb,ya)^cinab(xa,xb,yb)){
insert(i,j+tot);
insert(i+tot,j);
insert(j,i+tot);
insert(j+tot,i);
}
}
for(int i=1;i<=tot*2;i++)if(!dfn[i])dfs(i);
if(check())cout<<"YES"<<'\n';
else cout<<"NO"<<'\n';
}
return 0;
}
洛谷 P3209 [HNOI2010] 平面图判定的更多相关文章
- 洛谷P3209 [HNOI2010]平面图判定(2-SAT)
传送门 看到哈密顿回路就被吓傻了……结果没有好好考虑性质…… 首先,平面图有个性质:边数小于等于$3n-6$(我也不知道为啥),边数大于这个的直接pass 然后考虑原图,先把哈密顿回路单独摘出来,就是 ...
- P3209 [HNOI2010]平面图判定
P3209 [HNOI2010]平面图判定 哈密尔顿环之外的任意一条边,要么连在环内部,要么连在环外部 判断两条边在同一部分会相交,则这两条边必须分开 那么把边看作点连边,跑二分图染色就行 #incl ...
- Luogu P3209 [HNOI2010]平面图判定(2-SAT)
P3209 [HNOI2010]平面图判定 题意 题目描述 若能将无向图\(G=(V,E)\)画在平面上使得任意两条无重合顶点的边不相交,则称\(G\)是平面图.判定一个图是否为平面图的问题是图论中的 ...
- 洛谷P3209 [HNOI2010]PLANAR(2-SAT)
题目描述 若能将无向图G=(V,E)画在平面上使得任意两条无重合顶点的边不相交,则称G是平面图.判定一个图是否为平面图的问题是图论中的一个重要问题.现在假设你要判定的是一类特殊的图,图中存在一个包含所 ...
- 洛谷P3209 [HNOI2010]PLANAR
首先用一波神奇的操作,平面图边数m<=3*n-6,直接把m降到n, 然后对于冲突的边一条环内,一条环外,可以用并查集或者2Sat做, 当然并查集是无向的,2Sat是有向的,显然用并查集比较好 复 ...
- bzoj1997 [HNOI2010]平面图判定Plana
bzoj1997 [HNOI2010]平面图判定Planar 链接 bzoj luogu 思路 好像有很多种方法过去.我只说2-sat 环上的边,要不在里面,要不在外边. 有的边是不能同时在里面的,可 ...
- [BZOJ1997][HNOI2010] 平面图判定
Description Input Output 是的..BZOJ样例都没给. 题解(from 出题人): 如果只考虑简单的平面图判定,这个问题是非常不好做的. 但是题目中有一个条件— ...
- 洛谷P3203 [HNOI2010]弹飞绵羊(LCT,Splay)
洛谷题目传送门 关于LCT的问题详见我的LCT总结 思路分析 首先分析一下题意.对于每个弹力装置,有且仅有一个位置可以弹到.把这样的一种关系可以视作边. 然后,每个装置一定会往后弹,这不就代表不存在环 ...
- Bzoj2002/洛谷P3203 [HNOI2010]弹飞绵羊(分块)
题面 Bzoj 洛谷 题解 大力分块,分块大小\(\sqrt n\),对于每一个元素记一下跳多少次能跳到下一个块,以及跳到下一个块的哪个位置,修改的时候时候只需要更新元素所在的那一块即可,然后询问也是 ...
随机推荐
- Web GIS 航拍实现的智慧园区数字孪生应用
前言 随着智慧城市建设的不断发展,智慧园区作为智慧城市的先行区,其覆盖区域越来越大,产值越来越集中,对于园区数字化建设和智能化管理的诉求也愈加强烈.园区数字化管理是以实现园区多维度业务数据汇聚.融合. ...
- 2021ICPC网络赛第一场部分题解-The 2021 ICPC Asia Regionals Online Contest (I)
写在前面 本来应该6题的,结果不知道哪个铸币发了H的clar,当即把我们的思路转向三维几何上.当时我们还在想这三维计算几何的正确率有点太高了还在感叹ICPC选手的含金量,直到赛后我才知道这H题的铸币出 ...
- PHP中命名空间是怎样的存在(一)?
命名空间其实早在PHP5.3就已经出现了.不过大部分同学可能在各种框架的使用中才会接触到命名空间的内容,当然,现代化的开发也都离不开这些能够快速产出的框架.这次我们不从框架的角度,仅从简单的代码角度来 ...
- linux centos windows服务器修改数据库最大连接数的方法
1.可查询数据库最大连接数 show variables like '%max_connections%'; 2.修改数据库最大连接数,最大限制上限为16384. 找到数据库配置文件my.cnf,在配 ...
- JDBC-1(概述&建立)
基于宋红康老师所讲JDBC所作笔记 1.JDBC概述 1.1 数据持久化 持久化:将数据保持到可掉电式存储设备中以供之后使用. 数据持久化意味着将内存中的数据保存到硬盘上加以固化,实现过程大多通过各种 ...
- Java基础系列(9)- 数据类型扩展及常见面试题
整数拓展 // 整数拓展: 进制 二进制0b 十进制 八进制0 十六进制0x // 同一个数字在不同进制中,结果是不同的,进制换算 int i = 10; int i2 = 010; // 八进制 i ...
- Postman 如何调试加密接口?
大家好,我是安果! 众所周知,Postman 是一款非常流行且易用的 API 调试工具,在接口调试或测试时经常被使用针对普通 API 接口,我们可以直接在 Postman 中输入 URL.Query ...
- Windows下升级Python3.7.7后(原Python3.6.2版本)如何切换Python版本
笔者:风起怨江南 出处:https://www.cnblogs.com/mengjinxiang 笔者原创,文章欢迎转载,如果喜欢请点赞+关注,谢谢! 问题:window系统下,如果升级了最新的Pyt ...
- Nginx禁止ip方式访问80、443端口
在nginx.conf配置文件中 include /etc/nginx/conf.d/*.conf; 之前加入以下内容 server { listen 80 default; listen 443 d ...
- Flask SSTI利用方式的探索
Flask SSTI利用方式的探索 一.SSTI简介&环境搭建 一个统一风格的站点,其大多数页面样式都是一致的,只是每个页面显示的内容各不相同.要是所有的逻辑都放在前端进行,无疑会影响响应 ...