• 1617. Count Subtrees With Max Distance Between Cities


    问题:

    给定n个节点,以及节点直接的连线数组edges

    已知,这些节点代表城市,这些城市构成一棵树,

    即任意两节点都有唯一路径。

    求,这些城市中的子树中,各个最大路径的子树个数。

    Example 1:
    Input: n = 4, edges = [[1,2],[2,3],[2,4]]
    Output: [3,4,0]
    Explanation:
    The subtrees with subsets {1,2}, {2,3} and {2,4} have a max distance of 1.
    The subtrees with subsets {1,2,3}, {1,2,4}, {2,3,4} and {1,2,3,4} have a max distance of 2.
    No subtree has two nodes where the max distance between them is 3.
    
    Example 2:
    Input: n = 2, edges = [[1,2]]
    Output: [1]
    
    Example 3:
    Input: n = 3, edges = [[1,2],[2,3]]
    Output: [2,1]
     
    Constraints:
    2 <= n <= 15
    edges.length == n-1
    edges[i].length == 2
    1 <= ui, vi <= n
    All pairs (ui, vi) are distinct.

    Example 1:

    ⚠️ 注意:Example 1中所有的子树(至少有两个城市)有:

    [1,2] [2,3] [2,4]

    [1,2,3] [1,2,4]

    [1,2,3,4]

    而:

    [1,3] [1,4] [1,3,4]没有全联通,因此不算子树。

    解法:bitmask->Combination 组合。

    例如:state:1101

    代表组合:[1,2,4]

    代码做法:

    //遍历n个元素的组合: 
           for(int state=0; state<(1<<n); state++) {
                //bitmask to get combination
                ...
            }
    //翻译对应组合:
            for(int i=0; i<n; i++) {//对应元素 i: 0,1,2...n-1
                //this node i doesn't exist.
                if(((state>>i)&1) == 0) continue;
                //this node i exists.
                if(((state>>i)&1) == 1) {
                     ...
                }
            }

    本题解法:

    根据给出的【节点直接的连线数组edges】

    1. 创建任意两节点的距离数组distance:

      <1> 直接相连距离: 距离=1

    distance[i][j] == distance[j][i]

    由于节点无向,因此交换也保存。

      <2> 间接相连距离构建:距离=

    distance[i][j] = distance[i][k] + distance[k][j]

    2. 遍历所有组合:

    找到合法子树(node数==edge数+1)

    求最大距离。

    代码参考:

     1 class Solution {
     2 public:
     3     vector<vector<int>> distance;
     4     int getmaxdis(int state, int n) {//this state comb:0~n
     5         //state: 01101
     6         //city:  01234->{1,2,4}
     7         int maxdis = 0;
     8         int city_n = 0, edge_n = 0;
     9         for(int i=0; i<n; i++) {
    10             if(((state>>i)&1) == 0) continue;//this city i doesn't exist.
    11             city_n++;
    12             for(int j=i+1; j<n; j++) {
    13                 if(((state>>j)&1) == 0) continue;//this city j doesn't exist.
    14                 if(distance[i][j]==1)edge_n++;// 2 cities -> 1 edge
    15                 maxdis = max(maxdis, distance[i][j]);
    16             }
    17         }
    18         if(city_n!=edge_n+1) return 0;// invalid set which can't be a tree (like ex1: {1,3,4})
    19         return maxdis;
    20     }
    21     vector<int> countSubgraphsForEachDiameter(int n, vector<vector<int>>& edges) {
    22         vector<int>res(n-1, 0);
    23         int INF = n;//the max value of the set: n
    24         distance.resize(n, vector<int>(n, INF));
    25         for(vector<int>& edge:edges) {
    26             distance[edge[0]-1][edge[1]-1] = 1;
    27             distance[edge[1]-1][edge[0]-1] = 1;
    28         }
    29         //get all distance
    30         for(int k=0; k<n; k++) {//过渡节点
    31             for(int i=0; i<n; i++) {
    32                 for(int j=0; j<n; j++) {
    33                     distance[i][j] = min(distance[i][j], distance[i][k]+distance[k][j]);
    34                 }
    35             }
    36         }
    37         
    38         //for each set, get res
    39         for(int state=0; state<(1<<n); state++) {//bitmask to get combination
    40             int d = getmaxdis(state, n);
    41             if(d>0) res[d-1]++;
    42         }
    43         
    44         return res;
    45     }
    46 };
  • 相关阅读:
    记sql语句
    thinkPHP小记
    php操作目录和文件
    ubuntu搭配lamp
    phpStorm实用快捷键
    在wamp中www的文件夹(项目)打不开解决办法
    php正则表达式
    远程桌面,出现身份验证错误,要求的函数不正确,这可能是由于CredSSP加密Oracle修正
    discuz增加中文验证码
    react webpack 环境配置
  • 原文地址:https://www.cnblogs.com/habibah-chang/p/14400053.html
Copyright © 2020-2023  润新知