CodeForces

来源:互联网 发布:mac的远程桌面连接 编辑:程序博客网 时间:2024/06/06 02:32

The Tag Game 


Alice got tired of playing the tag game by the usual rules so she offered Bob a little modification to it. Now the game should be played on an undirected rooted tree of n vertices. Vertex 1 is the root of the tree.


Alice starts at vertex 1 and Bob starts at vertex x (x ≠ 1). The moves are made in turns, Bob goes first. In one move one can either stay at the current vertex or travel to the neighbouring one.


The game ends when Alice goes to the same vertex where Bob is standing. Alice wants to minimize the total number of moves and Bob wants to maximize it.


You should write a program which will determine how many moves will the game last.


Input
The first line contains two integer numbers n and x (2 ≤ n ≤ 2·105, 2 ≤ x ≤ n).


Each of the next n - 1 lines contains two integer numbers a and b (1 ≤ a, b ≤ n) — edges of the tree. It is guaranteed that the edges form a valid tree.


Output
Print the total number of moves Alice and Bob will make.


Example
Input
4 3
1 2
2 3
2 4
Output
4
Input
5 2
1 2
2 3
3 4
2 5
Output

6


题意:原题有每个案例的分析,但其实用处也不是很大,题目意思很简单,有Alice(以下用A表示)和Bob(以下用B表示),A和B在一棵树上,这棵树是由1~n这n个点构成,不同点之间有路径棵连通,第一行是n和x,后面的n-1行代表哪两个点之间有路径可以连通。现在A在点1上,B在点x上,A要尽可能节省步数来追上B,B要尽可能让A花更多的步数追上他,B可以选择移动一步或者不移动,A每次只能移动一步,和下棋类似B先走,A再走,无论B移动或不移动,都算作一步,要求的是A的步数加上B的步数。

分析:一开始以为要用DP,后来发现B一定是先走到某个位置然后一直不动,所以只要知道B最后停的位置,计算A到那个位置的最短路径即可,其中B要去的那个位置要保证是B先到,所以,要算两种最短路径,一个是A到所有点的最短路径,另一个是B所有点的最短路径,遍历所有点找到满足上述条件的点,并求出让A到满足条件点的最短路径路径中最大值。

代码如下:

#include<iostream>#include<cstdio>#include<map>#include<vector>#include<algorithm>#include<cstring>#include<queue>using namespace std;const int N=2e5+10,INF=0x3f3f3f3f;typedef pair<int,int> P;int step1[N],step2[N],x;map<int,vector<int> >m;void bfs1()//广搜求1到所有点的最短路径{    queue<int>q;    while(!q.empty())        q.pop();    q.push(1);    step1[1]=0;    while(!q.empty()){        int now=q.front();        q.pop();        for(vector<int>::iterator it=m[now].begin();it!=m[now].end();it++)            if(step1[now]+1<step1[(*it)]){                step1[(*it)]=step1[now]+1;                q.push((*it));            }    }}void bfs2()//广搜求x到所有点的最短路径{    queue<int>q;    while(!q.empty())        q.pop();    q.push(x);    step2[x]=0;    while(!q.empty()){        int now=q.front();        q.pop();        for(vector<int>::iterator it=m[now].begin();it!=m[now].end();it++)            if(step2[now]+1<step2[(*it)]){                step2[(*it)]=step2[now]+1;                q.push((*it));            }    }}int main(){    int n;    while(~scanf("%d%d",&n,&x)){        m.clear();        int a,b;        for(int i=1;i<n;i++){            scanf("%d%d",&a,&b);            m[a].push_back(b);//记录点可走的路径。            m[b].push_back(a);//因为是互通,所以两点都要记。        }        memset(step1,INF,sizeof(step1));//初始化        memset(step2,INF,sizeof(step2));        bfs1();bfs2();//调用函数        int maxl=0;        for(int i=2;i<=n;i++)            if(step1[i]>step2[i])//满足是B先到的这个点                maxl=max(maxl,step1[i]*2);//求最大值        printf("%d\n",maxl);    }    return 0;}