首先 想要尽可能拖延游戏时间 Bob必须躲在一个离Alice尽可能远的叶节点(度为1)
而怎样知道两人分别到每个叶节点的距离呢?
分别以两人位置为根 递归遍历整张树图 节点在第几层递归遇到 它就在第几层 离根节点的距离就是多少
再以与Alice距离为依据 将所有叶节点排序 距离长者优先考虑
但可能在Bob前往该地时会被Alice截击 也就是说Alice离该点更近
这条路行不通 考虑离Alice第二远的叶节点 总能找到答案
#include <stdio.h>
#include <queue>
#include <vector>
using namespace std;
struct node
{
friend bool operator< (node n1,node n2)
{
return n1.val<n2.val;
}
int id;
int val;
};
priority_queue <struct node> que;
vector <int> edge[400001];
int degree[200001],tem[200001],book[200001];
int dis1[200001],last1[200001];
int dis2[200001],last2[200001];
int n,m,s,num;
void safari1(int cur,int step);
void safari2(int cur,int step);
int main()
{
struct node t;
int i,a,b,ans;
while(scanf("%d%d",&n,&s)!=EOF)
{
m=n-1;
for(i=1;i<=n;i++)
{
edge[i].clear();
degree[i]=0;
}
while(!que.empty())
{
que.pop();
}
for(i=1;i<=m;i++)
{
scanf("%d%d",&a,&b);
edge[a].push_back(b);
edge[b].push_back(a);
degree[a]++,degree[b]++;
}
num=0;
for(i=1;i<=n;i++)
{
book[i]=0;
}
dis1[1]=0,last1[1]=-1,book[1]=1;
safari1(1,1);
for(i=1;i<=n;i++)
{
book[i]=0;
}
dis2[s]=0,last2[s]=-1,book[s]=1;
safari2(s,1);
for(i=1;i<=num;i++)
{
if(dis1[tem[i]]>dis1[s])
{
t.id=tem[i];
t.val=dis1[tem[i]];
que.push(t);
}
}
ans=dis1[s];
while(!que.empty())
{
t=que.top();
que.pop();
if(dis2[t.id]<dis1[t.id])
{
ans=dis1[t.id];
break;
}
}
printf("%d\n",ans*2);
}
return 0;
}
void safari1(int cur,int step)
{
struct node t;
int i;
if(degree[cur]==1)
{
num++;
tem[num]=cur;
if(cur!=1) return;
}
for(i=0;i<edge[cur].size();i++)
{
if(book[edge[cur][i]]==0)
{
dis1[edge[cur][i]]=step,last1[edge[cur][i]]=cur,book[edge[cur][i]]=1;
safari1(edge[cur][i],step+1);
}
}
return;
}
void safari2(int cur,int step)
{
int i;
if(cur!=s&°ree[cur]==1)
{
return;
}
for(i=0;i<edge[cur].size();i++)
{
if(book[edge[cur][i]]==0)
{
dis2[edge[cur][i]]=step,last2[edge[cur][i]]=cur,book[edge[cur][i]]=1;
safari2(edge[cur][i],step+1);
}
}
return;
}