题目链接:http://codeforces.com/problemset/problem/350/B
题意:有n个地方,给出n大小的序列a,0代表ai是山地,1代表ai是旅馆,再给出个n大小的序列v,第i的序列表示ai可以冲vi到达,问怎么走才能使路途最长(终点要是旅馆,而且路中途没有分叉)
思路:预处理每一个点的入度,每一个旅馆开始进行bfs(dfs应该也可以),直到该点有1个以上入度就该点就是路途的起点,记录最大值就可以
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#define maxn 100030
using namespace std;
int hot[maxn],ot[maxn],from[maxn],que[maxn],tem,save[maxn];
void bfs(int x)
{
int fr=0,re=-1;
if (from[x]!=0)
que[++re]=from[x];
while(fr<=re)
{
int u=que[fr++];//cout<<":"<<u<<endl;
if (ot[u]==1)
{
tem++;
if (from[u]!=0)
que[++re]=from[u];
}
}
}
int main()
{
int n;
while (scanf("%d",&n)!=EOF)
{
memset(ot,0,sizeof(ot));
for (int i=1;i<=n;i++)
{
scanf("%d",&hot[i]);
}
for (int i=1;i<=n;i++)
{
scanf("%d",&from[i]);
ot[from[i]]++;
}
int res=-1,beg,cnt=0;
for (int i=1;i<=n;i++)
{
if (hot[i]==1)
{//cout<<":"<<i<<endl;
tem=0;
bfs(i);
if (res<tem)
{
beg=i;
res=tem;
}
}
}
res++;
printf("%d\n",res);//cout<<":"<<beg<<endl;
while (cnt<res)
{
save[cnt++]=beg;
beg=from[beg];
}
for (int i=cnt-1;i>=0;i--)
{
printf("%d",save[i]);
if (i!=0) printf(" ");
else printf("\n");
}
}
}