图的遍历(2017-1-2,深度遍历)

图的遍历涉及到一个遍历数组的定义visited[N],数组元素的初始状态为0,当顶点Vi被访问过之后,就置visited[i]为1。

图的遍历方法通常分为:深度优先搜索法广度优先搜索法

 深度优先搜索算法:类似于树的前序遍历,是树的先根遍历的推广。

设G=(V,E)为任一无向图,从V(G)中任意一顶点v出发按照深度优先搜索法进行遍历的步骤如下:

  (1)设p为搜索指针,使p指向节点p;

  (2)访问p节点,然后使p指向与p相邻的且未曾访问的节点。

  (3)若p不空,则重复步骤(2),否则执行步骤(4).

  (4)沿着刚才访问的次序,反向回溯到一个尚有邻接顶点未曾访问过的节点,并使p指向这个未被访问的节点,然后重复步骤(2),直到所有节点都被访问到。

这个遍历过程是个递归过程,有个辅助全局变量visit[N]为记录各个节点是否有被访问过

根据不同的存储结构,算法描述也不同。

邻接矩阵的算法描述(深度优先搜索算法)

visited[N];

void DFS(graph *g)

{

  int i;

  for(i=0;i<g->n;i++)//初始化全局变量数组visited[N]

   visited[i]=0; //零代表了第i个节点没有被访问过 

  for(i=0;i<g->n;i++)//此处起到了(4)的作用

    if(!visited[i]) 

      DFSM(g,i);//或者DFSL(g,i);

}

void DFSM( graph *p,int i)//邻接矩阵上进行DFS遍历

{

  int j;

  printf("深度优先遍历结点:%c\n",g->vertex[i]);

  visited[i]=1;//假设g->vertex[i]为节点的编号,然后变访问标志为1

  for(j=0;j<g->n;j++)

    if(g->edges[i][j]==1&&!visited[j])//一个节点连有边时候,且该节点连结的另一个节点没有被访问过时候

      DFSM(g,j);//采用递归继续访问

}

void DFSL(graph *g,int i)//邻接表的深度查找算法

{

  pointer p;//节点类型

  printf("%d \n",g->adlist[i].data);//访问出发点,输出顶点数据

  visited[i]=1;

  for(p=g->adlist[n].first;p!=NULL;p=p->next)

    if(!visited[p->vertex])//节点未被访问过时候,就采用递归进行访问

      DFSL(g,p->vertex);

}

算法复杂度分析:

一个图有n个节点,e条边;

  DFSM的时间复杂度为O(n^2);

  DFSL的时间复杂度为O(n+e);

posted @ 2017-01-02 11:13  hai5111  阅读(343)  评论(0编辑  收藏  举报