码迷,mamicode.com
首页 > 其他好文 > 详细

图的深度优先搜索和广度优先搜索

时间:2014-12-17 16:33:23      阅读:245      评论:0      收藏:0      [点我收藏+]

标签:c   结构   存储   搜索   

此图是以图的邻接表法作为储存方式,对图进行深度优先搜索和广度优先搜索(均是非递归)

# include <stdio.h>
# include <stdlib.h>
# define True 1
# define False 0
# define Error -1
# define OK 1
# define MAX_VERTEX_NUM 20
int visited[MAX_VERTEX_NUM];
typedef char VertexData;

typedef enum{DG,DN,UDG,UDN} GraphKind;

typedef struct ArcNode{         //弧节点结构
 int adjvex;
 struct ArcNode *nextarc;
// OtherInfo info;
}ArcNode;

typedef struct VertexNode{       //表头节点结构
 VertexData data;
 ArcNode *firstarc;
}VertexNode;

typedef struct {
 VertexNode vertex[MAX_VERTEX_NUM];
 int vexnum,arcnum;
 GraphKind kind;
}AdjList;


//**********************关于栈的知识*******************************
typedef struct node
{
 int num;
 struct node *next;
}LinkStackNode, *LinkStack;

int InitStack(LinkStack *S)           //初始化栈
{
 (*S) = (LinkStack)malloc(sizeof(LinkStackNode));
 (*S)->next = NULL;
 if ((*S) != NULL)
  return True;
 else
  return False;
}

int Push(LinkStack S, int x)         //进栈
{
 LinkStack temp;
 temp = (LinkStack)malloc(sizeof(LinkStackNode));
 if (temp == NULL)
  return False;
 temp->num = x;
 temp->next  = S->next;
 S->next = temp;
 return True;
}

int Pop(LinkStack S, int *x)        //出栈
{
 LinkStack temp;
 temp = S->next;
 if (temp == NULL)
  return False;
 *x = temp->num;
 S->next = temp->next;
 free(temp);
 return True;
}

int IsEmpty(LinkStack S)        //判断栈是否为空
{
 if (S->next == NULL)
  return True;
 else
  return False;
}
//*************************************************************************

//****************************关于队的知识**********************************************
typedef struct Node
{
 int data;
 struct Node *next;
}LinkQueueNode;
typedef struct
{
 LinkQueueNode *front;
 LinkQueueNode *rear;
}LinkQueue;

int InitQueue(LinkQueue *Q)                //   链队列的初始化
{
 Q->front = (LinkQueueNode *)malloc(sizeof(LinkQueueNode));
 if (Q->front != NULL)
 {
  Q->rear = Q->front;
  Q->front->next = NULL;
  return (True);
 }
 else
  return False;
}

int EnterQueue(LinkQueue *Q, int x)             //链队列入队
{
 LinkQueueNode *NewNode;
 NewNode = (LinkQueueNode *)malloc(sizeof(LinkQueueNode));
 if (NewNode != NULL)
 {
  NewNode->data = x;
  NewNode->next = NULL;
  Q->rear->next = NewNode;
  Q->rear = NewNode;
  return True;
 }
 else
  return False;
}

int DeleteQueue(LinkQueue *Q, int *x)      //  链队列出队
{
 LinkQueueNode *p;
 if (Q->front == Q->rear)
  return False;
 p = Q->front->next;
 Q->front->next = p->next;
 if (Q->rear == p)
  Q->rear = Q->front;
 *x = p->data;
 free(p);
 return True;
}
int Empty(LinkQueue *Q)             //判断链栈是否为空
{
 if (Q->front == Q->rear)
  return True;
 else
  return  False;
}

//*************************************************************************************

int FirstAdjVertex(AdjList *g, int v)         //求v的第一个邻接点
{
 int w;
 ArcNode *p;
 p = g->vertex[v].firstarc;
 if (p == NULL)
  return Error;
 w = p->adjvex;
 return w;

}

int NextAdjVertex(AdjList *g, int v, int w)     //求v相对于w的下一个邻接点
{
 int k;
 ArcNode *p;
 p = g->vertex[v].firstarc;
 while (p->adjvex != w)
 {
  p = p->nextarc;
 }
 p = p->nextarc;
 if (p == NULL)
  return Error;
 else
 {
  k = p->adjvex;
  return k;
 }
}
int LocateVertex(AdjList *g, VertexData v)         //求顶点位置函数
{
 int j = Error,k;
 for (k = 0; k < g->vexnum ; k++)
  if (g->vertex[k].data  == v)
  {
   j = k;break;
  }
 return j;
}

void Crtadjlist(AdjList *g)            //创建邻接链表
{
 int n,e,i,j,k;
 char vt,vh;
 ArcNode *p;
 printf("请输入图的顶点个数和弧的个数\n");
 scanf("%d%d", &n, &e);
 g->vexnum  = n;
 g->arcnum  = e;
 printf("请输入顶点信息\n");
 getchar();
 for (i = 0; i < n; i++)
 {
  scanf("%c", &(g->vertex[i].data));
  g->vertex[i].firstarc = NULL;
 }
 printf("请输入弧的两个顶点\n");
 for (k = 0; k < e; k++)
 {
  getchar(); 
  scanf("%c%c",&vt,&vh);
  i = LocateVertex(g,vt);
  j = LocateVertex(g,vh);
  p = (ArcNode *)malloc(sizeof(ArcNode));
  p->adjvex = j;
  p->nextarc = g->vertex[i].firstarc;
  g->vertex[i].firstarc = p;
 }
}

void DepthFirstSearch(AdjList *g, int v0)  //深度优先搜索
{
 LinkStackNode *S;
 int v, w;
 InitStack(&S);
 Push(S, v0);
 while ( !IsEmpty(S))
 {
  Pop(S, &v);
  if (!visited[v])
  {
   printf("%c ",g->vertex[v].data );
   visited[v] = True;
   w = FirstAdjVertex(g,v);
   while (w != -1)
   {
    if (!visited[w])
     Push(S, w);
    w = NextAdjVertex(g,v,w);
   }
  }
 }
}
void TraverseGraph(AdjList *g)      //深搜
{
 int vi;
 for (vi = 0; vi < g->vexnum ; vi++)
  visited[vi] = False;               //初始化标志数组
 for (vi = 0; vi < g->vexnum; vi++)
  if (!visited[vi])
   DepthFirstSearch(g,vi);
}

void BreadthFirstSearch(AdjList *g, int v0)       // 广度优先搜索
{
 LinkQueue Q;
 int v, w;
 printf("%c ", g->vertex[v0].data);
 visited[v0] = True;
 InitQueue(&Q);
 EnterQueue(&Q,v0);
 while (!Empty(&Q))
 {
  DeleteQueue(&Q, &v);
  w = FirstAdjVertex(g, v);
  while (w != -1)
  {
   if (!visited[w])
   {
    printf("%c ",g->vertex[w].data);
    visited[w] = True;
    EnterQueue(&Q,w);
   }
   w = NextAdjVertex(g,v,w);
  }

 }

}
void BreadthTraverseGraph(AdjList *g)      //广搜
{
 int vi;
 for (vi = 0; vi < g->vexnum ; vi++)
  visited[vi] = False;               //初始化标志数组
 for (vi = 0; vi < g->vexnum; vi++)
  if (!visited[vi])
   BreadthFirstSearch(g,vi);
}

int main(void)
{
 AdjList g;
 Crtadjlist (&g);
 printf("深度优先搜索遍历输出\n");
 TraverseGraph(&g);
 printf("\n广度优先搜索遍历输出\n");
 BreadthTraverseGraph(&g);
 printf("\n");
 return 0;
}

图的深度优先搜索和广度优先搜索

标签:c   结构   存储   搜索   

原文地址:http://blog.csdn.net/java_oracle_c/article/details/41981663

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!