数据结构图的主要算法

数据结构定义

#define maxsize 100
邻接矩阵
typedef struct
{
	int no;
}VertexType;
typedef struct
{
	int edges[maxsize][maxsize];
	int n,e;
	VertexType vex[maxsize];
}MGraph;
邻接表
typedef struct ArcNode
{
	int adjvex;
	struct ANode *next;
}ArcNode;
typedef struct 
{
	ArcNode *firstarc;
}VNode;
typedef struct
{
	VNode adjlist[maxsize];
	int n,e;
}AGraph;

图的深度优先遍历

注:遍历过程中经过的边保留所形成的树,称为“深度优先搜索生成树”。

DFS递归实现
int visit[maxsize];
void DFS(AGraph *G,int v){
	ArcNode *p;
	Visit(v);
	visit[v]=1;
	p=G->adjlist[v].firstarc;
	while(p){
		if(visit[p->adjvex]==0)
			DFS(G,p->adjvex);
		p=p->nextarc;						
	}

}
DFS非递归实现
void DFS(AGraph *G,int v){
	int visit[maxsize];
	ArcNode *p;
	int stack[maxsize];int top=-1;
	int i,k;
	for(i=0;i<G->n;++i){
		visit[i]=0;
	}
	Visit(v);
	visit[v]=1;
	stack[++top]=v;
	while(top!=-1){
		k=stack[top];
		p=G->adjlist[k].firstarc;
		while(p!=NULL&&visit[p->adjvex]==1)
			p=p->nextarc;
		if(p==NULL)
			--top;
		else{
			Visit(p->adjvex);
			visit[p->adjvex]=1;
			stack[++top]=p->adjvex;
		}
	}
}

图的广度优先搜索遍历

void BFS(AGraph *G,int v,int visit[]){
	ArcNode *p;
	int que[maxsize];
	int front,rear;
	front=rear=0;
	int j;
	Visit(v);
	visit[v]=1;
	rear=(rear+1)%maxsize;
	que[rear]=v;
	while(front!=rear)
	{
		front=(front+1)%maxsize;
		j=que[front];
		p=G->adjlist[j].firstarc;
		while(p){
			if(visit[p->adjvex]==0)
			{
				rear=(rear+1)%maxsize;
				que[rear]=p->adjvex;
				visit[p->adjvex]=1;
				Visit(p->adjvex);

			}
			p=p->nextarc;
		}
	}
}

最小代价生成树

注:两个算法都是针对无向图的

普利姆算法

注:适用于稠密图

void Prim(MGraph g,int v0,int &sum){
 int lowcost[maxsize],vset[maxsize],v;
 int i,j,min,k;
 for(i=0;i<g.n;++i){
  lowcost[i]=g.edges[v0][i];
  vset[i]=0;
 }
 vset[v0]=1;
 sum=0;
 for(i=0;i<g.n-1;++i){
  min=INF;
  for(j=0;j<g.n;++j){
   if(vset[j]==0&&lowcost[j]<min){
    min=lowcost[j];
    k=j;
   }
   sum+=min;
   v=k;
   vset[v]=1;
   for(j=0;j<g.n;j++){
    if(vset[j]==0&&g.edges[v][j]<lowcost[j])
     lowcost[j]=g.edges[v][j];
   }
  }
 }
}
克鲁斯卡尔算法

注:适用于稀疏图

//克鲁斯卡尔算法
typedef struct 
{
 int a,b;
 int w;
}Road;
Road road[maxsize];
int v[maxsize];//并查集
int getRoot(int a){
 while(v[a]!=a)
  a=v[a];
 return a;
}
void Kruskal(MGraph g,int &sum,Road road[]){
 int i,j,a,b;
 sum=0;
 for(i=0;i<g.n;++i){
  v[i]=i;
 }
 sort(road,g.e);//一种排序算法,按照权值对各边排序
 for(i=0;i<g.e;++i){
  a=getRoot(road[i].a);
  b=getRoot(road[i].b);
  if(a!=b)
  {
   v[a]=b;
   sum+=road[i].w;
  }
 }
}

最短路径

迪杰斯特拉算法
//实现某一顶点到其余各顶点的最短路径
//打印路径函数
int PrintfPath(int path[],int a){
	int stack[maxsize],top=-1;
	while(path[a]!=-1)
	{stack[++top]=a;
	a=path[a];}
	stack[++top]=a;
	while(top!=-1)
	printf("%d",stack[top--]);
	
}
void Dijkstra(MGraph g,int v,int dist[],int path[]){
	int set[maxsize];
	int i,j,k;
	for(i=0;i<g.n;++i){
		dist[i]=g.edges[v][i];
		if(g.edges[v][i]<INF)//INF表示一个巨大的值
			path[i]=v;
		else
			path[i]=-1;
		set[i]=0;
	}
	set[v]=1;path[v]=-1;
	for(i=0;i<g.n-1;i++){
		int min=INF;
		for(j=0;j<g.n;j++){
			if(set[j]==0&&dist[j]<min)
			{
				min=dist[j];
				k=j;
			}
		}
		set[k]=1;
		for(j=0;j<g.n;j++){
			if(set==0&&dist[k]+g.edges[k][j]<dist[j])
			{
				dist[j]=dist[k]+g.edges[k][j];
				path[j]=k;
			}
		}
	}
}
弗洛伊德算法
//求图中任意一对顶点的最短路径
//打印最短路径
void printfPath(int u,int v,int path[][maxsize]){
	if(path[u][v]==-1)
	直接输出;
	else
	{
		int mid=path[u][v];
		printfPath(u,mid,path);
		printfPath(mid,v,path);
 	}

}
//时间复杂度O(n^3)
void Floyd(MGraph g,int path[][maxsize]){
	int A[maxsize][maxsize];
	int i,j,k;
	for(i=0;i<g.n;i++){
		for(j=0;j<g.n;j++){
			A[i][j]=g.edges[i][j];
			path[i][j]=-1;
		}
	}
	 for(k=0;k<g.n;k++){
 		 for(i=0;i<g.n;i++){
   			for(j=0;j<g.n;j++){
   				if(A[i][j]>A[i][k]+A[k][j])
   				{
   					A[i][j]=A[i][k]+A[k][]j;
   					path[i][j]=k;
   				}
   			}
		  }
	 }
}	

拓扑排序

注:针对有向无环图

typedef struct
{
	ArcNode *firstarc;
	int count;
}VNode;
int TopSSort(AGraph *G){
	int i,j,n=0;
	int stack[maxsize],top=-1;
	ArcNode *p;
	for(i=0;i<G->n;i++){
		if(G->adjlist[i].count==0)
		stack[++top]=i;
	}
	while(top!=-1)
	{
		j=stack[top--];
		n++;
		printf("%d",j);
		p=G->adjlist[j].firstarc;
		while(p){
		        G->adjlist[p->adjvex].count--;
		        if(G->adjlist[p->adjvex].count==0)
		        	stack[++top]=p->adjvex;
			p=p->nexarc;
		}
		if(n==G->n)
			return 1;
		else
			return 0;
	}
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值