1245. Tree Diameter

解题思路:本题是一道图的题目,但是无向图,给定的输入是图的各个边,题目中给出一个关键信息(Each node has labels in the set {0, 1, ..., edges.length})可知图中没有环,如果是有环的图这个题是无解的。最好的证明方法就是反正法,如果有环的话标号最大的节点必然小于边的数量,例如[0, 1], [1, 2], [0, 2], 三个节点且三条边,但编号最大的节点小于边的数量。

题目的解法依然是在图上做dfs寻找答案,因为是无向图,对于一个节点来说,可以从任何一个边进入,而从另外的边出去(除去只有一个边的节点,可以称为叶子节点),对于不同的入边,返回的答案是不一样的,对于已经计算过的从当前节点出去的边的最大长度也需要保存起来。

class Solution {
public:
    int recursive(vector<vector<int>>& graph, vector<map<int, int>>& memo, vector<bool>& visited, int cur){
        int len = 0;
        for(int i = 0; i < graph[cur].size(); ++i){
            int next = graph[cur][i];
            if(!visited[next]){
                visited[next] = true;
                if(memo[cur][next] == 0){
                    memo[cur][next] = recursive(graph, memo, visited, next) + 1;
                }
                len = max(len, memo[cur][next]); 
            }
        }
        return len;
    }
    
    int treeDiameter(vector<vector<int>>& edges) {
        const int nodeCnt = edges.size() + 1;
        vector<vector<int>> graph(nodeCnt, vector<int>());
        vector<map<int, int>> memo(nodeCnt, map<int, int>());
        for(auto edge : edges){
            graph[edge[0]].push_back(edge[1]);
            graph[edge[1]].push_back(edge[0]);
            memo[edge[0]][edge[1]] = 0;
            memo[edge[1]][edge[0]] = 0;
        }
        int ans = 0;
        for(int i = 0; i < graph.size(); ++i){
            if(graph[i].size() == 1){
                vector<bool> visited(nodeCnt, false);
                visited[i] = true;
                ans = max(ans, recursive(graph, memo, visited, i));
            }
        }
        return ans;
    }
};

  

posted @ 2019-11-14 13:48  蓝色地中海  阅读(337)  评论(0编辑  收藏  举报