ZBLOG

class DirectedGraph { private: int numVertices; vector adjacencyList; public: DirectedGraph(int n) : numVertices(n), adjacencyList(n) {} void addEdge(int u, int v, int weight) { adjacencyList[u].pu...

注释如下:

  1. class DirectedGraph {
  2. private:
  3. int numVertices; // 图中顶点的数量
  4. vector<vector<pair<int, int>>> adjacencyList; // 邻接表,存储每个顶点的出边和对应的权重
  5. public:
  6. DirectedGraph(int n) : numVertices(n), adjacencyList(n) {} // 构造函数,初始化图的顶点数量和邻接表大小
  7. void addEdge(int u, int v, int weight) {
  8. adjacencyList[u].push_back(make_pair(v, weight)); // 添加一条从顶点u到顶点v的有向边,并设置权重为weight
  9. }
  10. vector<int> topologicalSort() {
  11. vector<int> inDegree(numVertices, 0); // 记录每个顶点的入度
  12. for (int u = 0; u < numVertices; ++u) { // 遍历所有顶点
  13. for (auto& edge : adjacencyList[u]) { // 遍历当前顶点u的出边
  14. int v = edge.first; // 出边连接的顶点v
  15. ++inDegree[v]; // 递增顶点v的入度
  16. }
  17. }
  18. queue<int> q;
  19. for (int u = 0; u < numVertices; ++u) {
  20. if (inDegree[u] == 0) { // 将入度为0的顶点入队列
  21. q.push(u);
  22. }
  23. }
  24. vector<int> sortedOrder;
  25. while (!q.empty()) {
  26. int u = q.front();
  27. q.pop();
  28. sortedOrder.push_back(u); // 将当前顶点加入排序结果
  29. for (auto& edge : adjacencyList[u]) { // 遍历当前顶点的出边
  30. int v = edge.first; // 出边连接的顶点v
  31. --inDegree[v]; // 递减顶点v的入度
  32. if (inDegree[v] == 0) { // 如果顶点v的入度变为0,将其入队列
  33. q.push(v);
  34. }
  35. }
  36. }
  37. return sortedOrder; // 返回拓扑排序结果
  38. }
  39. void findCriticalPath() {
  40. vector<int> inDegree(numVertices, 0); // 记录每个顶点的入度
  41. for (int u = 0; u < numVertices; ++u) { // 遍历所有顶点
  42. for (auto& edge : adjacencyList[u]) { // 遍历当前顶点u的出边
  43. int v = edge.first; // 出边连接的顶点v
  44. ++inDegree[v]; // 递增顶点v的入度
  45. }
  46. }
  47. vector<int> startTime(numVertices, 0);
  48. vector<int> endTime(numVertices, 0);
  49. queue<int> q;
  50. for (int u = 0; u < numVertices; ++u) {
  51. if (inDegree[u] == 0) { // 将入度为0的顶点入队列
  52. q.push(u);
  53. }
  54. }
  55. while (!q.empty()) {
  56. int u = q.front();
  57. q.pop();
  58. for (auto& edge : adjacencyList[u]) { // 遍历当前顶点的出边
  59. int v = edge.first; // 出边连接的顶点v
  60. int weight = edge.second; // 边的权重
  61. inDegree[v]--;
  62. startTime[v] = max(startTime[v], startTime[u] + weight); // 计算顶点v的开始时间
  63. if (inDegree[v] == 0) { // 如果顶点v的入度变为0,将其入队列
  64. q.push(v);
  65. }
  66. }
  67. endTime[u] = startTime[u]; // 设置当前顶点u的结束时间等于开始时间(只有一个路径)
  68. }
  69. int criticalPathLength = *max_element(endTime.begin(), endTime.end()); // 找到关键路径长度
  70. cout << "Critical path length: " << criticalPathLength << endl;
  71. cout << "Critical path nodes: ";
  72. int currentNode = -1;
  73. for (int i = 0; i < numVertices; ++i) {
  74. if (endTime[i] == criticalPathLength && currentNode == -1) {
  75. currentNode = i;
  76. cout << currentNode << " "; // 输出关键路径上的第一个节点
  77. }
  78. else if (endTime[i] == criticalPathLength && startTime[i] == startTime[currentNode]) {
  79. currentNode = i;
  80. cout << currentNode << " "; // 输出和第一个节点具有相同开始时间的其他节点
  81. }
  82. }
  83. cout << endl;
  84. }
  85. };

以上是一个使用邻接表实现有向图的C++类,包含了添加边、拓扑排序和寻找关键路径等功能。


内容由零声教学AI助手提供,问题来源于学员提问

本站部分文章来源于网络,版权归原作者所有,如有侵权请联系站长删除。
转载请注明出处:https://golang.0voice.com/?id=16068

分享:
扫描分享到社交APP
上一篇
下一篇
发表列表
游客 游客
此处应有掌声~
评论列表

还没有评论,快来说点什么吧~

联系我们

在线咨询: 点击这里给我发消息

微信号:3007537140

上班时间: 10:30-22:30

关注我们
x

注册

已经有帐号?