写给自己做个备份的。
Kruskal Prim算法基本上是看别人的写的,Dijkstra Floyd算法是靠自己的理解写的。
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
#define UINT unsigned int
#define vexCounts 6
#define INF 0xFFFFFFFF
///Kruskal算法
///储存边的信息
struct Arc
{
int u;
int v;
UINT cost;
};
///Prim算法
///通过不断更新点到现有点的距离来取最短距离的点形成一个生成树
struct Node
{
UINT data;
UINT lowerestCost;
}Nodes[vexCounts];
///vextex 顶点
char vextex[] = { 'A', 'B', 'C', 'D', 'E', 'F' };
void AdjMatrix(unsigned int adjMat[][vexCounts])
{
for(int i=0;i<vexCounts;i++)
for(int j=0;j<vexCounts;j++)
{
if (i == j)
adjMat[i][j] = 0;
else
adjMat[i][j] = INF;
}
adjMat[0][1] = 6; adjMat[0][2] = 1; adjMat[0][3] = 5;
adjMat[1][0] = 6; adjMat[1][2] = 5; adjMat[1][4] = 3;
adjMat[2][0] = 1; adjMat[2][1] = 5; adjMat[2][3] = 5; adjMat[2][4] = 6; adjMat[2][5] = 4;
adjMat[3][0] = 5; adjMat[3][2] = 5; adjMat[3][5] = 2;
adjMat[4][1] = 3; adjMat[4][2] = 6; adjMat[4][5] = 6;
adjMat[5][2] = 4; adjMat[5][3] = 2; adjMat[5][4] = 6;
}
int Minmum(Node* node)
{
int index = -1;
unsigned lower = INF;
for(int i=0;i<vexCounts;i++)
{
if(node[i].lowerestCost<lower&&node[i].lowerestCost)
{
lower = node[i].lowerestCost;
index = i;
}
}
return index;
}
void Prim(unsigned int adjMat[][vexCounts],UINT idx)
{
Nodes[idx].data = idx;
Nodes[idx].lowerestCost = 0;
for (unsigned i = 0; i < vexCounts; i++) //初始化辅助数组
{
if (i != idx)
{
Nodes[i].data = idx;
Nodes[i].lowerestCost = adjMat[idx][i];
}
}
for(unsigned e=1;e<vexCounts;e++)
{
int min = Minmum(Nodes);
cout << vextex[Nodes[min].data] << "----" << vextex[min] << endl;
Nodes[min].lowerestCost = 0;
for(UINT i=0;i<vexCounts;i++)
{
if (!Nodes[i].lowerestCost) continue;
if(Nodes[i].lowerestCost>adjMat[min][i])
{
Nodes[i].lowerestCost = adjMat[min][i];
Nodes[i].data = min;
}
}
}
}
void ReadArc(UINT adjMat[][vexCounts],vector<Arc>& vertexArc)
{
Arc* tmp = NULL;
for(UINT i=0;i<vexCounts;i++)
{
for(UINT j=0;j<i;j++) ///因为是无向图只需要遍历一遍
{
if(adjMat[i][j]!=INF)
{
tmp = new Arc;
tmp->cost = adjMat[i][j];
tmp->u = i;
tmp->v = j;
vertexArc.push_back(*tmp);
delete tmp;
}
}
}
}
bool cmp(Arc a,Arc b)
{
return a.cost < b.cost;
}
bool FindTree(UINT a,UINT b,vector<vector<UINT>> &Tree)
{
UINT index_u = INF;
UINT index_v = INF;
for(int i=0;i<Tree.size();i++)
{
if (find(Tree[i].begin(), Tree[i].end(), a) != Tree[i].end())
index_u = i;
if (find(Tree[i].begin(), Tree[i].end(), b) != Tree[i].end())
index_v = i;
if (index_u != INF&&index_v != INF) break;
}
if(index_u!=index_v)
{
for(int i=0;i<Tree[index_v].size();i++)
{
Tree[index_u].push_back(Tree[index_v][i]);
}
Tree[index_v].clear();
return true;
}
else return false;
}
void Kruskal(UINT adjMat[][vexCounts])
{
vector<Arc> vertexArc;
int ct = 0;
ReadArc(adjMat, vertexArc);
sort(vertexArc.begin(), vertexArc.end(), cmp);
vector<vector<UINT>> Tree(vexCounts);
for(UINT i=0;i<vexCounts;i++)
{
Tree[i].push_back(i);
}
for(UINT i=0;i<vertexArc.size();i++)
{
UINT u = vertexArc[i].u;
UINT v = vertexArc[i].v;
if(FindTree(u,v,Tree))
{
ct++;
cout << vextex[u] << "----" << vextex[v] << endl;
}
if (ct == vexCounts - 1)break;
}
}
unsigned FindMin(UINT Dis[])
{
UINT min=INF,idx=0;
for (int i=0;i<vexCounts;i++)
{
if(min>Dis[i]&&Dis[i])
{
idx = i;
min = Dis[i];
}
}
return idx;
}
void ChangeDis(UINT adjMat[][vexCounts],UINT Distance[],UINT Dis[],UINT idx)
{
for(int i=0;i<vexCounts;i++)
{
if(Dis[i]&&adjMat[idx][i]!=INF&&(Distance[idx]+adjMat[idx][i])<Dis[i])
{
Dis[i]=Distance[idx] + adjMat[idx][i];
}
}
}
UINT Dis[vexCounts],Distance[vexCounts];
void Dijkstra(UINT adjMat[][vexCounts],int idx)
{
for(int i=0;i<vexCounts;i++)
{
Dis[i] = adjMat[i][idx];
}
Dis[idx] = 0;
Distance[idx] = 0;
for(int i=1;i<vexCounts;i++)
{
UINT min = FindMin(Dis);
Distance[min] = Dis[min];
Dis[min] = 0;
ChangeDis(adjMat, Distance, Dis, min);
}
}
void Floyd(UINT adjMat[][vexCounts])
{
UINT data[vexCounts][vexCounts];
memcpy(data, adjMat, sizeof(UINT)*vexCounts*vexCounts);
for(int i=0;i<vexCounts;i++)
{
for(int j=0;j<vexCounts;j++)
{
for(int k=0;k<vexCounts;k++)
{
if(data[j][i]!=INF&&data[i][k]!=INF)
data[j][k] = min(data[j][k], data[j][i] + data[i][k]);
}
}
}
for(int i=0;i<vexCounts;i++)
{
for(int j=0;j<vexCounts;j++)
{
cout << data[i][j] << '\t';
}
cout << endl;
}
}
int main()
{
UINT adjMat[vexCounts][vexCounts];
AdjMatrix(adjMat);
cout << "Prim" << endl;
Prim(adjMat, 0);
cout << "Kruskal" << endl;
Kruskal(adjMat);
Dijkstra(adjMat, 0);
for(int i=0;i<vexCounts;i++)
{
cout << Distance[i] << ' ';
}
cout << endl;
cout << "Floyd" << endl;
Floyd(adjMat);
return 0;
}