文件结构 :
示例图片 :
AdjacencyMatrix.cpp
//
// Created by A Luck Boy on 2023/2/5.
//
#include "AdjacencyMatrix.h"
void createInit(AMG & amg, int _vertex, int _edge, const char *sets){
amg.edge = _edge;
amg.vertex = _vertex;
for (int i=0;i<_vertex;i++){
amg.vexs[i] = sets[i];
}
// 默认权重最大
for (int i=0;i<_vertex;i++){
for (int j=0;j<_vertex;j++){
amg.matrix[i][j] = MAXLen;
}
}
};
static int getLocation(AMG amg, char _vexs){
// 不考虑不存在的情况了
for (int i=0;i<amg.vertex;i++){
if (amg.vexs[i] == _vexs){
return i;
} else{ continue;}
}
};
void allocate(AMG & amg, const int *args){
// 根据值获取二维矩阵的位置,比如 :示例中的5在矩阵的第二行第三列,索引对就是(1, 2)
int index = 0;
for (int i=0;i<amg.vertex-1;i++){
for (int j=1;j<amg.vertex-i;j++){
amg.matrix[i][i+j] = args[index];
amg.matrix[i+j][i] = args[index];
index++;
}
}
for (int i=0;i<amg.vertex;i++){
amg.matrix[i][i] = 0;
}
};
void show(AMG amg){
for (int i=0;i<amg.vertex;i++){
for (int ii=0;ii<amg.vertex;ii++){
if (amg.matrix[i][ii] == 1000){
cout << "1K" << " ";
} else{
cout << amg.matrix[i][ii] << " ";
}
}cout<<endl;
}
}
int getDegree(AMG amg, char _name){
// 老样子,不再写查询点是不是存在的
int _loc = getLocation(amg, _name);
// 第i行不等于0和MAXLen的数就记为一
int _count = 0;
for (int i=0;i<amg.vertex;i++){
if (amg.matrix[_loc][i] != 0 && amg.matrix[_loc][i] != MAXLen){
_count++;
} else{
continue;
}
}return _count;
};
int * getAllIndex(AMG amg, char _vexs){
int * allV = new int[getDegree(amg, _vexs)] ;
int curV_index = getLocation(amg, _vexs);
int index = 0;
for (int i=0;i<amg.vertex;i++){
if (amg.matrix[curV_index][i] != 0 && amg.matrix[curV_index][i] != MAXLen){
allV[index] = i;
index++;
}
}
return allV;
};
void _DFS(AMG amg, char _vexs, int * help_array){
// 让辅助数组元素初始化值全是0,表示没有访问,1表示被访问了
cout << "Visted Point " << _vexs << endl;
// 这个数组每个元素对于名字字符串的每个字符名字的顺序
// 获取每次起点的索引并记录该点已被访问
int from_index = getLocation(amg, _vexs);
help_array[from_index] = 1;
// 与该点相连接的所有点的索引组成的数组
int * arr = getAllIndex(amg, _vexs);
for (int d=0;d< getDegree(amg, _vexs);d++){
// 如果没被遍历
if (help_array[arr[d]] == 0) { _DFS(amg, amg.vexs[arr[d]], help_array); }
else { continue; }
}
};
void DFS(AMG amg, char _vexs){
int * help_array =new int[amg.vertex]() ;
_DFS(amg, _vexs, help_array);
};
AdjacencyMatrix.h
//
// Created by A Luck Boy on 2023/2/5.
//
#include <iostream>
using namespace std;
#define Waring cout <<"代码有误!"<<endl;
// 表示极大值,即便或者弧的最大权重不可以超过这个值,而且此值代表两点之间不存在边
#define MAXLen 1000
// 允许的最大顶点数目以及顶点类型
#define SIZE 10
typedef struct AdjacencyMatrixGraph{
// 顶点集合
char vexs[SIZE];
// 矩阵实体——默认操作数据类型是整型
int matrix[SIZE][SIZE];
// 图的当前点数和边数
int vertex, edge;
}AMG;
// methods
// 声明 : 不会检测一些常见bug——比如传入边长是5,那应该有25个数据,结果只传入了23个等等等
// 初始化,确定顶点数和边数,然后初始化矩阵,让默认权值设为MAXLen
// 参数说明 : _vertex是顶点数目, int _edge是边数, char *sets是字符顶点集合组成的字符串(比如说 :顶点是a、b、c三个,参数就是abc)
// 当然了,sets不可以出现重复的字符
void createInit(AMG & amg, int _vertex, int _edge, const char *sets);
// 获取点k在构造时一维数组的位置
static int getLocation(AMG amg, char _vexs);
// 分配实质权重,注意 : 无向图中由于邻接矩阵主对角线上全是0,而且矩阵关于主对角线对称
// 所以 : 假设nxn的矩阵,主对角线上是n个0,剩下你只需要输入(n-1)n/2个数据,顺序是从第一行n-1个元素往第n-1行的1个元素
/* 0 1 2 3
* 1 0 5 4
* 2 5 0 7
* 3 4 7 0
* 这里的参数就是1、2、3、5、4、7
* */
// 切记 : 如果两点之间没有边,仍然要传入MAXLen或者1000来表示无连接
void allocate(AMG & amg, const int *args);
// 以矩阵形式展示出来
void show(AMG amg);
// 获取某顶点的度
int getDegree(AMG amg, char _vexs);
// 获取与某点连接的所有点的索引组成的数组,数组长度也就是该点的度
int * getAllIndex(AMG amg, char _vexs);
// 深度优先算法
// 算法中需要实现一个数组用来辅助判断某个点是否被访问过
// 在邻接矩阵中,如果数据1000或者MMAXLEN或者0则表示此处两点之间无边
// _vexs表示的是从哪个顶点开始
// 对于非连通图,可以判断某个点的度是否为0确定,从而不可以使用DFS算法,但是这里不考虑这么细了,默认全是连通图
void _DFS(AMG amg, char _vexs, int * help_array);
void DFS(AMG amg, char _vexs);
main.cpp
//
// Created by A Luck Boy on 2023/2/5.
//
#include "AdjacencyMatrix.h"
int main(){
AMG amg;
// 对如图所示的图建立邻接矩阵
createInit(amg, 6, 6, "ABCDEF");
const int array[] = {1, 2, MAXLen, 5, MAXLen, MAXLen, 3, MAXLen,
MAXLen, 4, MAXLen, MAXLen, MAXLen, MAXLen, 6};
allocate(amg, array);
show(amg);
// 获取每个点的度
for (int i=0;i<amg.vertex;i++) cout << "Point " << amg.vexs[i ]
<< " Degree is "<<getDegree(amg,amg.vexs[i]) << endl;
// 获取各个点连接的点
for (int i=0;i<amg.vertex;i++){
char cur_V = amg.vexs[i];
int * arr = getAllIndex(amg, cur_V);
for (int j=0;j< getDegree(amg, cur_V);j++){
cout << "Point " << cur_V << "-----" << amg.vexs[arr[j]]<<endl;
}
}
DFS(amg, 'B');
return 0;
}
终端运行结果
0 1 2 1K 5 1K
1 0 1K 3 1K 1K
2 1K 0 4 1K 1K
1K 3 4 0 1K 1K
5 1K 1K 1K 0 6
1K 1K 1K 1K 6 0
Point A Degree is 3
Point B Degree is 2
Point C Degree is 2
Point D Degree is 2
Point E Degree is 2
Point F Degree is 1
Point A-----B
Point A-----C
Point A-----E
Point B-----A
Point B-----D
Point C-----A
Point C-----D
Point D-----B
Point D-----C
Point E-----A
Point E-----F
Point F-----E
Visted Point B
Visted Point A
Visted Point C
Visted Point D
Visted Point E
Visted Point F
源代码 : 自己实现的数据结构与算法合集: 自己实现的数据结构与算法合集,使用C或者C++ - Gitee.com
备注 : 2023.2.12晚7:54,降雨,但是对于DFS代码bug的修改的成功可谓灵光乍现……