882. Reachable Nodes In Subdivided Graph
阿新 • • 發佈:2018-08-16
graph java代碼 elf mov des public self vector !=
題目鏈接
https://leetcode.com/contest/weekly-contest-96/problems/reachable-nodes-in-subdivided-graph/
解題思路
1)題目要求,經過m步後,可以到達的點,等價於求有多少點距離起點的最短距離小於等於m,即這是一個單源最短路徑問題,使用djstra算法
復雜度
時間 o(eloge)
空間復雜度o(e). e為邊數
本解決方案的註意點
1)計數時,節點和邊上的點要分開計數,防止重復計算節點
2)使用優先隊列保存邊,會有重復的節點出現,需要過濾下
java代碼
class Node { public int src; public int move; public Node(int src, int move) { this.src = src; this.move = move; } } public class Solution { public int reachableNodes(int[][] edges, int M, int N) { Map<Integer, Map<Integer, Integer>> graph = new HashMap<>(); for (int i = 0; i < N; i++) { graph.put(i, new HashMap<>()); } Map<Integer, Boolean> visited = new HashMap<>(); Queue<Node> pq = new PriorityQueue<>((a, b) -> (a.move - b.move)); //build graph for (int[] v : edges) { graph.get(v[0]).put(v[1], v[2]); graph.get(v[1]).put(v[0], v[2]); } int result = 0; Node head = new Node(0, 0); pq.offer(head); while (!pq.isEmpty()) { Node cur = pq.peek(); pq.poll(); int src = cur.src; int move = cur.move; if (null != visited.get(src)) continue; visited.put(src, true); ++result; for (int id : graph.get(src).keySet()) { int dst = id; int weight = graph.get(src).get(dst); int nextMove = move + weight + 1; if (null != visited.get(dst)) { result += Math.min(M - move, graph.get(src).get(dst)); } else { if (nextMove > M) { result += M - move; graph.get(dst).put(src, graph.get(dst).get(src) - (M - move)); } else { result += weight; graph.get(dst).put(src, 0); Node next = new Node(dst, nextMove); pq.offer(next); } } } } return result; } }
c++代碼
class Node { public: int src; int move; Node(int a, int b) { this->src = a; this->move = b; } }; class MyCmp { public: bool operator() (const Node& l, const Node& r) { return l.move > r.move; } }; class Solution { public: int reachableNodes(vector<vector<int>>& edges, int M, int N) { unordered_map<int, unordered_map<int, int>> graph; unordered_map<int, bool> visited; priority_queue<Node, vector<Node>, MyCmp> pq; //build graph for (vector<int> v : edges) { graph[v[0]][v[1]] = v[2]; graph[v[1]][v[0]] = v[2]; } int result = 0; Node head(0, 0); pq.push(head); while (!pq.empty()) { Node cur = pq.top(); pq.pop(); int src = cur.src; int move = cur.move; if (move > M) break; //may be duplicated if (visited[src]) continue; visited[src] = true; result++; //travel array for (auto& it : graph[src]) { int dst = it.first; int weight = it.second; int nextMove = move + weight + 1; if (visited[dst]) { result += min(M - move, graph[src][dst]); } else { if (nextMove > M) { result += M - move; graph[dst][src] -= M - move; } else { result += weight; graph[dst][src] = 0; Node next(dst, nextMove); pq.push(next); } } } } return result; } };
python代碼
class Solution(object): def reachableNodes(self, edges, M, N): """ :type edges: List[List[int]] :type M: int :type N: int :rtype: int """ # hashmap graph = {} visited = {} pq = [] result = 0 for i in range(N): graph[i] = {} for i, j, l in edges: graph[i][j] = graph[j][i] = l # print graph heapq.heappush(pq, (0, 0)) while pq: move, src = heapq.heappop(pq) # print move, "==", src if move > M: break if src in visited: continue visited[src] = 1 result = result + 1 for dst in graph[src]: weight = graph[src][dst] next_move = move + weight + 1 if dst in visited: result += min(M - move, graph[src][dst]) else: if next_move > M: result += M - move graph[dst][src] -= M - move else: result += weight graph[dst][src] = 0 heapq.heappush(pq, (next_move, dst)) return result
882. Reachable Nodes In Subdivided Graph