试实现普里姆最小生成树算法。
一、函数接口定义:
void Prim(AMGraph G, char u);
其中 G 是基于邻接矩阵存储表示的无向图,u表示起点
二、裁判测试程序样例:
#include <iostream>
#define MVNum 10
#define MaxInt 32767
using namespace std;
struct edge{
char adjvex;
int lowcost;
}closedge[MVNum];
typedef struct{
char vexs[MVNum];
int arcs[MVNum][MVNum];
int vexnum,arcnum;
}AMGraph;
int LocateVex(AMGraph G , char v);//实现细节隐藏
int Min(AMGraph G);//实现细节隐藏
int CreateUDN(AMGraph &G);//实现细节隐藏
void Prim(AMGraph G, char u);
int main(){
AMGraph G;
CreateUDN(G);
char u;
cin >> u;
Prim(G , u);
return 0;
}
/* 请在这里填写答案 */
三、输入样例:
第1行输入结点数vexnum和边数arcnum。第2行输入vexnum个字符表示结点的值,接下来依次输入arcnum行,每行输入3个值,前两个字符表示结点,后一个数表示两个结点之间边的权值。最后一行输入一个字符表示最小生成树的起始结点。
7 9
0123456
0 1 28
0 5 10
1 2 16
1 6 14
2 3 12
3 6 18
3 4 22
4 5 25
4 6 24
0
四、输出样例:
按最小生成树的生成顺序输出每条边。
0->5
5->4
4->3
3->2
2->1
1->6
全部代码如下:
#include <iostream>
#define MVNum 10
#define MaxInt 32767
using namespace std;
struct edge {
char adjvex;
int lowcost;
} closedge[MVNum];
typedef struct {
char vexs[MVNum];
int arcs[MVNum][MVNum];
int vexnum, arcnum;
} AMGraph;
int LocateVex(AMGraph G, char v)
{
// 实现细节隐藏
// 这个函数用于定位顶点 v 在图 G 中的位置,返回顶点在 vexs 数组的下标
// 可以使用 for 循环遍历 vexs 数组,找到与 v 匹配的顶点并返回下标
for (int i = 0; i < G.vexnum; i++) {
if (G.vexs[i] == v) {
return i;
}
}
return -1; // 如果 v 不在 vexs 数组中,则返回 -1
}
int Min(AMGraph G)
{
// 实现细节隐藏
// 这个函数用于从 closedge 数组中选择权值最小的边并返回其下标
// 可以使用循环遍历 closedge 数组,找到权值最小的边并返回其下标
int minCost = MaxInt;
int minIndex = -1;
for (int i = 0; i < G.vexnum; i++) {
if (closedge[i].lowcost < minCost && closedge[i].lowcost != 0) {
minCost = closedge[i].lowcost;
minIndex = i;
}
}
return minIndex;
}
int CreateUDN(AMGraph& G)
{
// 实现细节隐藏
// 这个函数用于创建无向带权图 G
// 可以根据需要设置图的顶点数和边数,并通过键盘输入顶点和边的信息
// 可以使用嵌套循环来输入每条边的权值,如果两个顶点之间没有边,可以将对应位置的边权值设置为 MaxInt
cout << "请输入顶点数和边数:";
cin >> G.vexnum >> G.arcnum;
cout << "请输入" << G.vexnum << "个顶点(用空格分隔):";
for (int i = 0; i < G.vexnum; i++) {
cin >> G.vexs[i];
}
for (int i = 0; i < G.vexnum; i++) {
for (int j = 0; j < G.vexnum; j++) {
G.arcs[i][j] = MaxInt;
}
}
cout << "请输入" << G.arcnum << "个边的信息(起点 终点 权值):";
for (int k = 0; k < G.arcnum; k++) {
char v1, v2;
int weight;
cin >> v1 >> v2 >> weight;
int i = LocateVex(G, v1);
int j = LocateVex(G, v2);
G.arcs[i][j] = weight;
G.arcs[j][i] = weight; // 无向图,边是双向的,需要添加两条边
}
return 0;
}
void Prim(AMGraph G, char u)
{
int uIndex = LocateVex(G, u);
for (int i = 0; i < G.vexnum; i++) {
if (i != uIndex) {
closedge[i].adjvex = u;
closedge[i].lowcost = G.arcs[uIndex][i];
}
}
closedge[uIndex].lowcost = 0;
for (int k = 1; k < G.vexnum; k++) {
int minIndex = Min(G);
cout << closedge[minIndex].adjvex << " -> " << G.vexs[minIndex] << endl;
closedge[minIndex].lowcost = 0;
for (int i = 0; i < G.vexnum; i++) {
if (G.arcs[minIndex][i] < closedge[i].lowcost) {
closedge[i].adjvex = G.vexs[minIndex];
closedge[i].lowcost = G.arcs[minIndex][i];
}
}
}
}
int main()
{
AMGraph G;
CreateUDN(G);
char u;
cout << "请输入起始顶点:";
cin >> u;
Prim(G, u);
return 0;
}
标签:vexnum,char,普里,int,最小,MVNum,closedge,AMGraph,算法
From: https://www.cnblogs.com/yzx-sir/p/17493680.html