美团点评2019年校招编程题——图的遍历

##1.题目描述
给定一张包含N个点,N-1条边的无向连通图,节点从1到N编号,每条边长度为1。假设你从1号节点出发并打算遍历所有节点,那么路程至少是多少?
输入描述:

第一行输入一个整数N,1<=N<=10^5
接下来N-1行,每行包含两个数X,Y,表示X号节点到Y号节点之间有一条线,1<=X,Y<=N

输出描述:

输出总路径的最小值

样例输入:

4
1 2
1 3
3 4

样例输出:

4

##2.分析
以下述例子分析

		1
	  / | \
	 2  3  5
	    |   \
	    4    6
	          \
	           7
	       
	        

可以看出,这个图,其实就是一颗普通树,那么1遍历的最短路径应该是:

1->2->1->3->4->3->1->5->6->7

其实,我们看出来,1节点到叶子节点有三条路径,分别是:

1->5->6->7 1->2  1->3->4  

那么,我们队这三条路径长度从小到大排序,就是

1->2  1->3->4  1->5->6->7 

那么我们更加每条路径长度推出节点1遍历路径的最小路程应该是:

2*(2-1)+2*(3-1)+(4-1)

所以,就是求根节点1到每条叶子节点的路径,从小到大排序,之后得到结果就很简单了。
##3.代码

#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
void findPath(vector<vector<int>>& lujin,int node,vector<int> &path)
{
    auto iter = std::find(path.begin(),path.end(),node);
    if(iter == path.end())
    {
        path.push_back(node);
        for(int i=0;i<lujin[node].size();++i)
        {
            findPath(lujin,lujin[node][i],path);
        }
    }
}

void findPath(vector<vector<int>>& lujin,vector<vector<int>>& paths)
{
    for(int i=0;i<lujin[0].size();++i)
    {
        vector<int> path;
        path.push_back(0);
        int node = lujin[0][i];
        findPath(lujin,node,path);
        paths.push_back(path);

    }
}
int main()
{
    int n;
    cin>>n;
    vector<vector<int>> lujin(n,vector<int>(0));
    for(int i=0;i<n-1;++i)
    {
        int x,y;
        cin>>x>>y;
        lujin[x-1].push_back(y-1);
        lujin[y-1].push_back(x-1);
    }
    //如果是样例输入,那么lujin的结果应该是:
    //lujin[0]:1,2
    //lujin[1]:0
    //lujin[2]:0,3
    //lujin[3]:2
    vector<vector<int>> paths;
    findPath(lujin,paths);
    //paths的结果应该是:
    //paths[0]:0,1
    //paths[1]:0,2,3

    vector<int> result;
    for(int i=0;i<paths.size();++i)
    {
        result.push_back(paths[i].size());
    }
    std::sort(result.begin(),result.end());
    //result结果是:2,3
    int count=0;
    for(auto iter=result.begin();iter!=result.end()-1;++iter)
    {
        count +=2*(*iter-1);
    }
    count +=*(result.end()-1)-1;
    cout<<count<<endl;
    return 0;
}

猜你喜欢

转载自blog.csdn.net/zqw_yaomin/article/details/82493202