输入输出样例
示例
输入
9
3 4 2 5 3 8 4 6 9
输出
4
样例解释
如下图所示,崇拜关系用箭头表示,红色表示不在圈中。
显然,最大圈是[2 4 5 3] 构成的圈。
运行限制
- 最大运行时间:1s
- 最大运行内存: 256M
分析:
这题简单来说就是找一个最大圈。
如何去找一个最大圈呢,很容易想是从起点出发一直到终点,而且这个终点也是我们的起点就好了,有点像DFS一直往下找对吧。没错就是深搜。
什么时候终止呢?其实我们从一个点往下找圈无非两种情况:一种是能找到圈,一种是成不了圈。对前一种情况需要拿圈的边数和答案取最大值,对于第二种情况直接退出就好了。
如何实现这样的判别呢?很容易想到用visit[]的bool数组来判断是否走到过这个边,如果下面一个点的visit[]是true(已经访问过)并且到达了原来的起点,那么就是成圈的,如果下一个点已经访问过并且下一个点不是起点,那么其实是找圈失败的。
其中visit记得要回溯,以免对后续的起点查找造成影响。
代码如下所示:
#include <iostream>
using namespace std;
const int MAXN=100001;
int worship[MAXN];
bool visit[MAXN];
int n,ans;
//k代表第几个人 step表示从第i个人走了多少步
void dfs(int k,int step,int goal)
{
if(visit[k]&&k!=goal) return;
if(visit[k]&&k==goal)
{
if(step>ans) ans=step;
return;
}
visit[k]=true;
int next=worship[k];
dfs(next,step+1,goal);
visit[k]=false;
}
int main()
{
// 请在此输入您的代码
cin>>n;
for(int i=1;i<=n;++i)
{
cin>>worship[i];
}
for(int i=1;i<=n;++i)
{
visit[i]=true;
dfs(worship[i],1,i);
}
cout<<ans;
return 0;
}