[Informe del experimento de matemáticas discretas] Generación del árbol de expansión mínimo

Experimento 4: árbol de expansión mínimo

1. Propósito del experimento:

Comprender cómo dibujar un árbol de expansión mínima. Mejore la capacidad de los estudiantes para escribir informes experimentales y resumir los resultados experimentales, y cultive la capacidad de pensamiento lógico de los estudiantes y las ideas de diseño de algoritmos. Capaz de completar de forma independiente el diseño y análisis de algoritmos simples, usarlos aún más para resolver problemas prácticos, ayudar a los estudiantes a aprender y dominar los métodos básicos de programación en lenguaje C y C ++ y varios métodos de depuración, para que los estudiantes tengan la capacidad de programación.

2. Contenido experimental:

Dado un gráfico ponderado, encuentre su árbol de expansión mínimo

3. Principio experimental

evitación de círculos o ruptura de círculos

4. Código de programa y resultados experimentales

inserte la descripción de la imagen aquí

#include <iostream>
#include <vector>
#include <limits>

using namespace std;

const int MAX = 100;
const int INF = numeric_limits<int>::max();  // 定义 INF 为 int 类型的最大值
vector<vector<int>> result(MAX,vector<int>(2,0));

// prim 算法函数,计算最小生成树的权值并返回
int prim(vector<vector<int>> &graph) {
    
    
    int n = graph.size();  // 获取图中节点数
    vector<bool> visited(n, false);  // 标记节点是否已被访问过
    vector<int> minDist(n, INF);  // 记录节点到最小生成树的最短距离
    vector<int> parent(n, -1);  // 记录节点在最小生成树中的父节点
    minDist[0] = 0;  // 从第 0 个节点开始,到自身的距离为 0
    int res = 0;  // 最小生成树的权值

    for (int i = 0; i < n; ++i) {
    
      // 进行 n 次遍历,每次加入一个节点
        int u = -1;  // 记录当前未访问节点中,距离最小生成树最近的节点
        for (int j = 0; j < n; ++j) {
    
      // 寻找未访问节点中距离最小生成树最近的节点
            if (!visited[j] && (u == -1 || minDist[j] < minDist[u])) {
    
    
                u = j;
            }
        }
        cout<<"最小生成树各边如下:"<<endl;

        visited[u] = true;  // 标记该节点已被访问
        if (parent[u] != -1) {
    
      // 输出加入最小生成树的边的权值和信息
            result[i-1][0] = parent[u]+1;
            result[i-1][1] = u+1;
            cout << parent[u] + 1 << "-" << u + 1 << ":" << minDist[u] << endl;
        }
        res += minDist[u];  // 将该节点到最小生成树的最短距离加入最小生成树的权值中

        for (int v = 0; v < n; ++v) {
    
      // 更新未被访问节点到最小生成树的最短距离
            if (!visited[v] && graph[u][v] < minDist[v]) {
    
    
                minDist[v] = graph[u][v];
                parent[v] = u;  // 记录 v 在最小生成树中的父节点为 u
            }
        }
    }

    return res;  // 返回最小生成树的权值
}

int main() {
    
    
    // 定义邻接矩阵表示的图
    /*
     vector<vector<int>> graph = {
        {0, 1, 2, INF, INF},
        {1, 0, 4, 2, INF},
        {2, 4, 0, 3, 5},
        {INF, 2, 3, 0, 1},
        {INF, INF, 5, 1, 0}
    };

    */
    vector<vector<int>> graph(7, vector<int>(7, INF));

    cout<<"请输入你要为这6个顶点添加的边数:"<<endl;
    int n;
    cin>>n;
    cout<< "请为编号为1-6的这六个顶点添加边,格式为:V1-V2:W" <<endl;
    int a,b,w;

    for(int i = 1; i <= n; i++){
    
    
         scanf("%d-%d:%d",&a,&b,&w);
         graph[a-1][b-1] = graph[b-1][a-1] = w;
    }



    // 输出最小生成树的权值
   prim(graph);


    return 0;
}

resultado

inserte la descripción de la imagen aquí

Supongo que te gusta

Origin blog.csdn.net/Yaoyao2024/article/details/131087385
Recomendado
Clasificación