#include<stdio.h>
#include<string.h>
//表结点,采用邻接表存储图
#include<iostream>
#include<string>
#include<stack>
using namespace std;
//表结点
struct ArcNode {
ArcNode * next; //下一个关联的边
int adjvex; //保存弧尾顶点在顶点表中的下标
};
//顶点表
struct Vnode {
string data; //顶点名称
ArcNode * firstarc; //第一个依附在该顶点边
};
class Graph_DG {
private:
int vexnum; //图的顶点数
int edge; //图的边数
int * indegree; //每条边的入度情况
Vnode * arc; //邻接表
public:
Graph_DG(int, int);
~Graph_DG();
//检查输入边的顶点是否合法
bool check_edge_value(int,int);
//创建一个图
void createGraph();
//打印邻接表
void print();
//进行拓扑排序,Kahn算法
bool topological_sort();
//进行拓扑排序,DFS算法
bool topological_sort_by_dfs();
void dfs(int n,bool * & visit, stack<string> & result);
};
//初始化 vexnum:顶点个数,edge:边数
Graph_DG::Graph_DG(int vexnum, int edge)
{
this->vexnum = vexnum;
this->edge = edge;
this->arc = new Vnode[this->vexnum];
this->indegree = new int[this->vexnum]; //每个顶点的入度数目
for (int i = 0; i < this->vexnum; i++) {
this->indegree[i] = 0;
this->arc[i].firstarc = NULL;
this->arc[i].data = "v" + to_string(i + 1);
}
}
void Graph_DG::createGraph() {
int count = 0;
int start, end;
cout << "输入每条起点和终点的顶点编号(从1开始编号)" << endl;
while (count != this->edge) {
cin >> start;
cin >> end;
//检查边是否合法
while (!this->check_edge_value(start, end)) {
cout << "输入的顶点不合法,请重新输入" << endl;
cin >> start;
cin >> end;
}
//声明一个新的表结点
ArcNode * temp = new ArcNode;
temp->adjvex = end - 1;
temp->next = NULL;
//如果当前顶点的还没有边依附时,
if (this->arc[start - 1].firstarc == NULL) {
this->arc[start - 1].firstarc = temp;
}
else {
ArcNode * now = this->arc[start - 1].firstarc;
while(now->next) {
now = now->next;
}//找到该链表的最后一个结点
now->next = temp;
}
++count;
}
}
void Graph_DG::print() {
int count = 0;
cout << "图的邻接矩阵为:" << endl;
//遍历链表,输出链表的内容
while (count != this->vexnum) {
//输出链表的结点
cout << this->arc[count].data<<" ";
ArcNode * temp = this->arc[count].firstarc;
while (temp) {
cout<<"<"<< this->arc[count].data<<","<< this->arc[temp->adjvex].data<<"> ";
temp = temp->next;
}
cout << "^" << endl;
++count;
}
}
//非递归的方式去深度优先遍历图
void DFS(Graph_DG G,int startnode)
{
vector<int> visit(vexnum,0);
stack<int> s;
s.push(startnode);
visit[startnode] =1;
ArcNode * temp = this->arc[startnode].firstarc;
while(!s.empty())
{
temp =this->arc[s.top()].firstarc; //栈顶
while(temp)
{
if(visit[temp->adjvex]==0)
{
visit[temp->adjvex]==1;
printf("2%d");
s.push(temp->adjvex);
temp=this->arc[temp->adjvex].firstarc;
}
else //
{
temp =temp->next;
}
}
if(temp==NULL)
{
s.pop();
}
}
}
数据结构-图的深度优先遍历方式(非递归,邻接表存储)
于 2022-08-12 10:58:48 首次发布