hdu 1689 Alien’s Necklace (bfs层次图剪枝)
Alien’s Necklace
Time Limit: 10000/5000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 1526 Accepted Submission(s): 415
Unfortunately, only particular pairs of balls can be adjacent in the necklace, otherwise they will explode. Notice that the first and the last ball in the necklace are also adjacent. Besides, the Martians think even numbers are unlucky, so the number of balls
in the necklace must be odd. (Of course each ball can be used only once)
A necklace contains at least 3 balls. Because the balls are really precious, JYY wants the necklace has as few balls as possible. (Then he can give rest balls to his GF)
So JYY wonders the number of balls he has to use to make this necklace.
For each input, the first line contains 2 numbers N and M, N is the number of balls JYY collected, and M is the pairs of compatible balls. Balls are numbered from 1 to N. Followed M lines, each contains 2 numbers A and B, means that ball A and ball B are compatible.
For each case, 0 < N <= 1,000, 0 < M <= 20,000.
2
5 6
1 2
2 4
1 3
3 5
4 3
4 5
2 1
1 2
Case 1: JYY has to use 3 balls.
Case 2: Poor JYY.
题意:让找到一个环使得组成环的点数为奇数且点数至少为3,。
由于一个点能够多个途径到达,但从一点出发第一次到达的肯定是最短路径,又题目要求的奇偶性,每次到达一个点步数的奇偶性进行标记。
#include<stdio.h>
#include<algorithm>
#include<queue>
#include<string.h>
#include<vector>
using namespace std;
#define N 1005
#define ll __int64
const int inf=0x7fffffff;
vector<int>g[N];
int vis[N][2];
struct node
{
int u,t;
friend bool operator<(node a,node b)
{
return a.t>b.t;
}
};
int bfs(int s)
{
int i,u,v;
priority_queue<node >q;
node cur,next;
cur.u=s;
cur.t=1;
memset(vis,0,sizeof(vis));
vis[s][1]=1; //奇数点。用一个珠子
q.push(cur);
while(!q.empty())
{
cur=q.top();
q.pop();
u=cur.u;
for(i=0;i<g[u].size();i++)
{
next.u=v=g[u][i];
next.t=cur.t+1;
if(v==s&&next.t%2==0&&next.t>3) //结点处到达两次。故应该减一
return next.t-1;
if(!vis[v][next.t%2])
{
vis[v][next.t%2]=1;
q.push(next);
}
}
}
return inf;
}
int main()
{
int i,n,m,u,v,tt,cnt=0;
scanf("%d",&tt);
while(tt--)
{
scanf("%d%d",&n,&m);
for(i=1;i<=n;i++)
g[i].clear();
while(m--)
{
scanf("%d%d",&u,&v);
g[u].push_back(v);
g[v].push_back(u);
}
int ans=inf;
for(i=1;i<=n;i++)
ans=min(ans,bfs(i));
if(ans==inf)
printf("Case %d: Poor JYY.\n",++cnt);
else
printf("Case %d: JYY has to use %d balls.\n",++cnt,ans);
}
return 0;
}
以下这样的方法是用一个数组记录到达该点的步数,当再次訪问该点时。说明出现环,直接推断奇偶性就能够了。
又要求所用珠子数目大于三,所以要用一个pre变量记录上一个节点的标号,推断是否是两点直接成环。
#include<stdio.h>
#include<algorithm>
#include<queue>
#include<string.h>
#include<vector>
using namespace std;
#define N 1005
#define ll __int64
const int inf=0x7fffffff;
vector<int>g[N];
int vis[N][2];
int ans;
struct node
{
int u,t,pre;
friend bool operator<(node a,node b)
{
return a.t>b.t;
}
};
int bfs(int s)
{
int i,u,v,t;
priority_queue<node >q;
node cur,next;
cur.u=s;
cur.t=1;
cur.pre=-1;
memset(vis,0,sizeof(vis));
vis[s][1]=1;
q.push(cur);
while(!q.empty())
{
cur=q.top();
q.pop();
u=cur.u;
for(i=0;i<g[u].size();i++)
{
next.u=v=g[u][i];
next.t=cur.t+1;
next.pre=u;
if(v==cur.pre)
continue;
if(vis[v][0]) //偶数点
{
t=cur.t+vis[v][0];
if(t%2==0)
return t-1;
}
else if(vis[v][1])
{
t=cur.t+vis[v][1];
if(t%2==0)
return t-1;
}
else
{
vis[v][next.t%2]=next.t;
q.push(next);
}
}
}
return inf;
}
int main()
{
int i,n,m,u,v,tt,cnt=0;
scanf("%d",&tt);
while(tt--)
{
scanf("%d%d",&n,&m);
for(i=1;i<=n;i++)
g[i].clear();
while(m--)
{
scanf("%d%d",&u,&v);
g[u].push_back(v);
g[v].push_back(u);
}
ans=inf;
for(i=1;i<=n;i++)
ans=min(ans,bfs(i));
if(ans==inf)
printf("Case %d: Poor JYY.\n",++cnt);
else
printf("Case %d: JYY has to use %d balls.\n",++cnt,ans);
}
return 0;
}
hdu 1689 Alien’s Necklace (bfs层次图剪枝)的更多相关文章
- POJ3967Ideal Path[反向bfs 层次图]
Ideal Path Time Limit: 10000MS Memory Limit: 65536K Total Submissions: 1754 Accepted: 240 Descri ...
- hdu 1689 求奇环bfs关键是层次图
#include<stdio.h> #include<string.h> #include<stdlib.h> #include<queue> usin ...
- UVA 1599, POJ 3092 Ideal Path 理想路径 (逆向BFS跑层次图)
大体思路是从终点反向做一次BFS得到一个层次图,然后从起点开始依次向更小的层跑,跑的时候选则字典序最小的,由于可能有多个满足条件的点,所以要把这层满足条件的点保存起来,在跑下一层.跑完一层就会得到这层 ...
- hdu 1044 BFS(压缩图)+DFS
题意: 给你起点,终点,图上有墙有路还有宝物,问你在规定时间内能否能到终点,如果能问最多能捡到多少宝物. 思路: 看完这个题目果断 BFS+三维的mark ...
- 使用Architecture Explorer分析应用程序及使用层次图
使用Architecture Explorer分析应用程序 Architecture Explorer和依赖图可以帮助我们了解所有的项目,包括小项目和大项目.Architecture Explorer ...
- HDU 2717 Catch That Cow --- BFS
HDU 2717 题目大意:在x坐标上,农夫在n,牛在k.农夫每次可以移动到n-1, n+1, n*2的点.求最少到达k的步数. 思路:从起点开始,分别按x-1,x+1,2*x三个方向进行BFS,最先 ...
- UIKit框架类层次图
学习UIKit应该首选了解UIKit类的层次图,从根类一层一层的拨.
- uva 10983 Buy one, get the rest free 二分判定层次图
二分枚举租用飞机的最大花费,然后用小于等于最大花费的边构建层次图(依据时间) 构图思路: 利用二元组(x,y)表示 x天y城市 1. e天有飞机从a城市飞到b城市,能够承载x人,则添加单向边 ( ...
- HDU.1689 Just a Hook (线段树 区间替换 区间总和)
HDU.1689 Just a Hook (线段树 区间替换 区间总和) 题意分析 一开始叶子节点均为1,操作为将[L,R]区间全部替换成C,求总区间[1,N]和 线段树维护区间和 . 建树的时候初始 ...
随机推荐
- ssh 免密码登录 与 密钥公钥原理讲解
前言 由于最近频繁需要登录几个服务器,每次登录都需要输入密码,故相对麻烦. 由于个人服务器用于实验,故对安全性要求不是很高,故想实现ssh免密登录. 通过阅读ssh 公钥私钥认证操作及原理以及ssh公 ...
- PAT Basic 1055
1055 集体照 拍集体照时队形很重要,这里对给定的 N 个人 K 排的队形设计排队规则如下: 每排人数为 N/K(向下取整),多出来的人全部站在最后一排: 后排所有人的个子都不比前排任何人矮: 每排 ...
- python基础学习笔记——列表技巧
列表: 循环删除列表中的每⼀个元素 li = [, , , ] for e in li: li.remove(e) print(li) 结果: [, ] 分析原因: for的运⾏过程. 会有⼀个指针来 ...
- Working out (DP)
Summer is coming! It's time for Iahub and Iahubina to work out, as they both want to look hot at the ...
- 通过 Terracotta实现基于Tomcat的Web应用集群
[转]通过 Terracotta实现基于Tomcat的Web应用集群 博客分类: 企业应用面临的问题 Java&Socket 开源组件的应用 tomcatweb session集群服务器负载均 ...
- Python 频繁读取Mysql相关问题
1.需要频繁select大量数据,时间长.消耗内存大,如何解决mysql性能问题? 如果对返回的结果数量没有要求,可以控制返回的数量: cursor.fetchmany(size=1000) 这样是只 ...
- BZOJ 1191: [HNOI2006]超级英雄Hero【二分图匹配】
裸的匹配题,一眼就能看出来二分图的模型,是某个经典题的改编.貌似某本图论书上讲过的,有N个人以及M个职位,每个职位只能提供给一个人,而每个人由于能力有限只能胜任有限个职位,问是否有办法使得每个人都有工 ...
- 染色(bzoj 2243)
Description 给定一棵有n个节点的无根树和m个操作,操作有2类: 1.将节点a到节点b路径上所有点都染成颜色c: 2.询问节点a到节点b路径上的颜色段数量(连续相同颜色被认为是同一段),如“ ...
- wamp Apache和mysql服务无法启动的终极解决方法!!!!!!
用了几年的wampserver 突然宣告无法启动,Apache和mysql都崩溃了,在计算机的服务选项里面也是无法启动的,系统报了一个未知错误,重装了N个版本的PHP集成开发环境,都宣告失败! 我想应 ...
- Codevs 1299 切水果 水一发
时间限制: 1 s 空间限制: 128000 KB 题目等级 : 大师 Master 题目描述 Description 简单的说,一共N个水果排成一排,切M次,每次切[L,R]区间的所有水果(可能有的 ...