无向图的完美消除序列 判断弦图 ZOJ 1015 Fish net
题意简述:给定一个无向图,判断是否存在一个长度大于3的环路,且其上没有弦(连接环上不同两点的边且不在环上)。
命题等价于该图是否存在完美消除序列。
所谓完美消除序列:在 vi,vi+1,...vn vi与之后与vi相邻的点构成一个团(完全子图)。
求完美消除序列的MCS算法。倒序给点标号,标号为i的点出现在序列的第i项。对每个顶点i,维护标号label[i],表示标号的度,每次选择标号最大的点标号。用堆加速。
求出了完美消除序列后,只要判断这个序列是否合法就可以得出结论。
在 vi,vi+1,...vn的导出子图中找到与vi相邻的标号最小(度最小)的点,设为vj,再检查vj是否与每个vi的邻接点相邻。
#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<cmath>
#include<vector>
#include<queue>
#include<algorithm>
#include<set>
#define clr(x,y) memset(x,y,sizeof(x))
using namespace std;
const int maxn=1010; vector<int> construct(int n,vector<int> adj[maxn])
{
static int rank[maxn],label[maxn];
clr(rank,-1);clr(label,0);
priority_queue<pair<int,int> > heap; for(int i=1;i<=n;i++)
heap.push(make_pair(0,i)); for(int i=n-1;i>=0;i--)
{
while(true)
{
int u=heap.top().second;heap.pop();
if(rank[u]==-1)
{
rank[u]=i;
for(vector<int>:: iterator iter=adj[u].begin();iter!=adj[u].end();++iter)
{
if(rank[*iter]==-1)
{
label[*iter]++;
heap.push(make_pair(label[*iter],*iter));
}
}
break;
}
}
}
vector<int> result(n);
for(int i=1;i<=n;i++)
{
result[rank[i]]=i;
}
return result;
} bool check(int n,vector<int>adj[maxn],vector<int> ord)
{
static bool mark[maxn];
static int rank[maxn];
for(int i=0;i<n;i++)rank[ord[i]]=i;
clr(mark,0);
for(int i=0;i<n;i++)
{
vector<pair<int,int> >tmp;
for(vector<int>::iterator iter=adj[ord[i]].begin();iter!=adj[ord[i]].end();++iter)
if(!mark[*iter])tmp.push_back(make_pair(rank[*iter],*iter)); sort(tmp.begin(),tmp.end());
if(tmp.size())
{
int u=tmp[0].second;set<int> tmpAdj;
for(vector<int>::iterator iter=adj[u].begin();iter!=adj[u].end();++iter)
{
tmpAdj.insert(*iter);
}
for(int i=1;i<(int)tmp.size();++i)
{
if(!tmpAdj.count(tmp[i].second))return false;
}
}
mark[ord[i]]=true;
}
return true;
} bool is_chordal(int nodeCount,vector<pair<int,int> >edges)
{
int n=nodeCount;
vector<int>adj[maxn];
for(int i=0;i<=n;i++)
adj[i].clear();
for(vector<pair<int,int> >::iterator iter=edges.begin();iter!=edges.end();++iter)
{
adj[iter->first].push_back(iter->second);
adj[iter->second].push_back(iter->first);
}
return check(n,adj,construct(n,adj));
} int main()
{
int n,m;
while(scanf("%d%d",&n,&m))
{
if(n==0&&m==0)return 0;
vector<pair<int,int> >ed;
for(int i=0;i<m;i++)
{
int a,b;
scanf("%d%d",&a,&b);
ed.push_back(make_pair(a,b));
}
if(is_chordal(n,ed))printf("Perfect\n\n");
else printf("Imperfect\n\n");
}
return 0;
}
完美消除序列还有广泛的应用,以后来补充。
无向图的完美消除序列 判断弦图 ZOJ 1015 Fish net的更多相关文章
- ZOJ 1015 Fishing Net(判断弦图)
题目链接:http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemId=15 题意:给定一个图.判断是不是弦图? 思路:(1)神马是弦图?对于一 ...
- BZOJ 1006 完美消除序列&最大势算法&弦图
K国是一个热衷三角形的国度,连人的交往也只喜欢三角原则.他们认为三角关系:即AB相互认识,BC相互认识,CA相互认识,是简洁高效的.为了巩固三角关系,K国禁止四边关系,五边关系等等的存在.所谓N边关系 ...
- bzoj 1006: [HNOI2008]神奇的国度 弦图的染色问题&&弦图的完美消除序列
1006: [HNOI2008]神奇的国度 Time Limit: 20 Sec Memory Limit: 162 MBSubmit: 1788 Solved: 775[Submit][Stat ...
- bzoj 1006 [HNOI2008]神奇的国度 弦图+完美消除序列+最大势算法
[HNOI2008]神奇的国度 Time Limit: 20 Sec Memory Limit: 162 MBSubmit: 4370 Solved: 2041[Submit][Status][D ...
- 【BZOJ】1006: [HNOI2008]神奇的国度 弦图消除完美序列问题
1006: [HNOI2008]神奇的国度 Description K国是一个热衷三角形的国度,连人的交往也只喜欢三角原则. 他们认为三角关系:即AB相互认识,BC相互认识,CA相互认识,是简洁高效的 ...
- ZOJ 1015 Fishing Net(弦图判定)
In a highly modernized fishing village, inhabitants there make a living on fishery. Their major tool ...
- ●BZOJ 1006 [HNOI2008]神奇的国度(弦图最小染色数)○ZOJ 1015 Fishing Net
●赘述题目 给出一张弦图,求其最小染色数. ●题解 网上的唯一“文献”:<弦图与区间图>(cdq),可以学习学习.(有的看不懂) 摘录几个解决改题所需的知识点: ●子图和诱导子图(一定要弄 ...
- [bzoj1242] Zju1015 Fishing Net弦图判定
弦图判定..MCS算法. 先选一个点,然后每次拿 相邻已选点最多 的未选点. 选完之后判断一下是否是完美消除序列. #include<cstdio> #include<iostrea ...
- BZOJ 1006: [HNOI2008]神奇的国度(弦图)
传送门 解题思路 弦图就是图中任意一个大小\(>=4\)的环至少存在一条两个节点不相邻的边,这样的图称为弦图,弦图有许多优美的性质.一个无向图是弦图当且仅当它有一个完美消除序列,完美消除序列就是 ...
随机推荐
- ubuntu 16.04 php 安装curl方法
先查看自己的php是否已经安装了curl.方法如下:1.在web服务器目录( Ubuntu下的通常为 /var/www )新建test.php文件2.编辑文件,键入下面一行代码:<?php ph ...
- python 开发者 精品
当 Python 和 R 遇上北京二手房 http://mp.weixin.qq.com/s?timestamp=1473262097&src=3&ver=1&signatur ...
- Struts2的那些小细节
1.result中传多个参数,&不允许使用需要转义&即多个参数之间用&隔开 <result type="redirectAction">show ...
- 【腾讯Bugly干货分享】你为什么需要 Kotlin
本文来自于腾讯Bugly公众号(weixinBugly),未经作者同意,请勿转载,原文地址:http://mp.weixin.qq.com/s/xAFKGarHhfQ3nKUwPDlWwQ 一.往事 ...
- linux 5个查找命令
1. find find是最常见和最强大的查找命令,你可以用它找到任何你想找的文件. find的使用格式如下: $ find <指定目录> <指定条件> <指定动作> ...
- Express4.x安装
1.首先肯定是要安装Node.JS npm install -g expressnpm install -g express-generator 运行express -V输出 4.9.0 2.创建一个 ...
- es6笔记3^_^object
一.destructuring ES6允许按照一定模式,从数组和对象中提取值,对变量进行赋值,这被称为解构Destructuring. //es5 if(1){ let cat = 'ken'; le ...
- [linux]ngrep命令、常见用法
1.ngrep命令 ngrep命令是grep命令的网络版,ngrep用于搜寻指定的数据包(抓包.过滤).能识别TCP.UDP和ICMP包,理解bpf的过滤机制. 1.1 安装 brew install ...
- HDU5914
Triangle Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/65536 K (Java/Others)Total Su ...
- CodeForces 460B
Little Dima and Equation Time Limit:1000MS Memory Limit:262144KB 64bit IO Format:%I64d & ...