图论简述+图论考试要点(C++)

图论基本概念

图论是研究图(Graph)的数学理论,图由**顶点(Vertex)边(Edge)**组成,用于表示对象及其关系。

  • 无向图:边无方向,用无序对 (u, v) 表示。
  • 有向图:边有方向,用有序对 (u \\to v) 表示。
  • 权重图:边附带权值,常用于路径优化问题。
  • 常见术语:度(Degree)、路径(Path)、环(Cycle)、连通性(Connectedness)。

图的存储方式(C++实现)

邻接矩阵

适用于稠密图,空间复杂度 O(V\^2)

cpp 复制代码
const int MAX_V = 100;
int adjMatrix[MAX_V][MAX_V]; // 初始化为0或INF
邻接表

适用于稀疏图,空间复杂度 O(V + E)

cpp 复制代码
#include <vector>
vector<int> adjList[MAX_V]; // 无权重
vector<pair<int, int>> weightedAdjList[MAX_V]; // 带权重

图遍历算法

深度优先搜索(DFS)

递归或栈实现,用于连通性检测、拓扑排序等。

cpp 复制代码
bool visited[MAX_V];
void dfs(int u) {
    visited[u] = true;
    for (int v : adjList[u]) {
        if (!visited[v]) dfs(v);
    }
}
广度优先搜索(BFS)

队列实现,用于最短路径(无权图)。

cpp 复制代码
queue<int> q;
bool visited[MAX_V];
void bfs(int start) {
    q.push(start);
    visited[start] = true;
    while (!q.empty()) {
        int u = q.front(); q.pop();
        for (int v : adjList[u]) {
            if (!visited[v]) {
                visited[v] = true;
                q.push(v);
            }
        }
    }
}

最短路径算法

Dijkstra算法

适用于非负权图,时间复杂度 O((V + E) \\log V)

cpp 复制代码
priority_queue<pair<int, int>, vector<pair<int, int>>, greater<pair<int, int>>> pq;
vector<int> dist(MAX_V, INF);
void dijkstra(int start) {
    dist[start] = 0;
    pq.push({0, start});
    while (!pq.empty()) {
        auto [d, u] = pq.top(); pq.pop();
        if (d > dist[u]) continue;
        for (auto [v, w] : weightedAdjList[u]) {
            if (dist[v] > dist[u] + w) {
                dist[v] = dist[u] + w;
                pq.push({dist[v], v});
            }
        }
    }
}
Floyd-Warshall算法

动态规划实现,适用于所有节点对的最短路径,时间复杂度 O(V\^3)

cpp 复制代码
int dist[MAX_V][MAX_V];
void floydWarshall(int V) {
    for (int k = 0; k < V; ++k)
        for (int i = 0; i < V; ++i)
            for (int j = 0; j < V; ++j)
                dist[i][j] = min(dist[i][j], dist[i][k] + dist[k][j]);
}

最小生成树(MST)

Kruskal算法

基于并查集,时间复杂度 O(E \\log E)

cpp 复制代码
struct Edge { int u, v, w; };
vector<Edge> edges;
int parent[MAX_V];

int find(int u) { return parent[u] == u ? u : parent[u] = find(parent[u]); }

int kruskal() {
    sort(edges.begin(), edges.end(), [](Edge a, Edge b) { return a.w < b.w; });
    for (int i = 0; i < MAX_V; ++i) parent[i] = i;
    int total = 0;
    for (Edge e : edges) {
        int pu = find(e.u), pv = find(e.v);
        if (pu != pv) {
            parent[pu] = pv;
            total += e.w;
        }
    }
    return total;
}
Prim算法

优先队列实现,时间复杂度 O(E \\log V)

cpp 复制代码
priority_queue<pair<int, int>, vector<pair<int, int>>, greater<pair<int, int>>> pq;
bool inMST[MAX_V];
int prim() {
    pq.push({0, 0});
    int total = 0;
    while (!pq.empty()) {
        auto [w, u] = pq.top(); pq.pop();
        if (inMST[u]) continue;
        inMST[u] = true;
        total += w;
        for (auto [v, weight] : weightedAdjList[u]) {
            if (!inMST[v]) pq.push({weight, v});
        }
    }
    return total;
}

拓扑排序

适用于有向无环图(DAG),基于DFS或BFS(Kahn算法)。

cpp 复制代码
vector<int> topoSort(int V) {
    vector<int> inDegree(V, 0), result;
    for (int u = 0; u < V; ++u)
        for (int v : adjList[u]) inDegree[v]++;
    queue<int> q;
    for (int u = 0; u < V; ++u)
        if (inDegree[u] == 0) q.push(u);
    while (!q.empty()) {
        int u = q.front(); q.pop();
        result.push_back(u);
        for (int v : adjList[u]) {
            if (--inDegree[v] == 0) q.push(v);
        }
    }
    return result.size() == V ? result : vector<int>(); // 检查环
}

关键考点总结

  1. 基础概念:图的分类、术语(度、连通分量等)。
  2. 存储与遍历:邻接表/矩阵的选择,DFS/BFS的应用场景。
  3. 算法实现:Dijkstra、Floyd、Kruskal、Prim的代码模板。
  4. 拓扑排序:DAG的判定与排序方法。
  5. 复杂度分析:各算法的时间/空间复杂度比较。

建议结合实际问题(如LeetCode、OJ题目)练习代码实现。

相关推荐
Teleger1 天前
在window上使用c++控制鼠标点击,实现的exe
c++·单片机·计算机外设
June`1 天前
高并发内存池如何实现
c++·tcmalloc·内存池
ComputerInBook1 天前
C++ 关键字 constexpr 和 consteval 之注意事项
开发语言·c++·constexpr·consteval
米啦啦.1 天前
STL(标准模板库)
开发语言·c++·stl
咩咦1 天前
C++学习笔记08:指针和引用的区别
c++·学习笔记·指针·引用·指针和引用
洛水水1 天前
【力扣100题】34.二叉搜索树中第K小的元素
c++·算法·leetcode
许长安1 天前
gRPC Keepalive 机制
c++·经验分享·笔记·rpc
wangjialelele1 天前
Linux SystemV 消息队列 + 责任链模式:实现客户端消息处理流水线
linux·服务器·c语言·网络·c++·责任链模式
智者知已应修善业1 天前
51单片机4按键控制共阳LED霓虹灯切换1整体闪烁2流水下3流水上4间隔闪烁】2023-10-27
c++·经验分享·笔记·算法·51单片机
洛水水1 天前
结构性设计模式详解
c++·设计模式