图的深度优先遍历-C语言实现

Posted 礼彬fly

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了图的深度优先遍历-C语言实现相关的知识,希望对你有一定的参考价值。

我在大二上学期期末时候写的,大概2014年1月4号左右。我写在博客里一是为我以后复习所用,二是希望对需要的人有所帮助。

问题描述:

设计一个程序,输入一个无向图的顶点(编号 1,2,3···n)和边,使用邻接表存储结构存储该图,设定起始顶点后,按深度优先遍历算法遍历该图。输出顶点的访问次序。


#include<stdio.h>

#include<stdlib.h>
#include<malloc.h>
#include<string.h>
#define MAXLIN 40
/*----邻接表存储结构---*/
//-----------------表节点存储结构----------
typedef struct ArcNode                                            //结构体
    int adjvex;     //表节点编号信息
    struct ArcNode *next;   
ArcNode;
//-----------------头结点存储结构-----------
typedef struct VNode            
    char vertex[5];      //节点信息
    ArcNode *link;
    int id;         //编号
VNode;
//边节点
typedef struct Bian                            //为了方便 加的一个结构体
    char one[5];                //存储边的第一个节点
    char two[5];                //存储边的第二个节点
Bian;
typedef struct
    VNode adjList[MAXLIN];     //顺序存储 头结点  头结点的数组
    int vexnum;       //顶点数
    int arcnum;            //边数
    Bian bian[MAXLIN];        //边的数组
    int kind;                //图的存储种类
ALGraph;
int visit[MAXLIN];
//返回是第几个顶点
int PanDuan(char n[5],ALGraph &G)

    for(int i=0;i<G.vexnum;i++)
    
        if(strcmp(n,G.adjList[i].vertex)==0)
        return i;
    
    printf("没有找到相关顶点,图的信息有误!\\n");
    return 0;

//输入图的相关信息  
ALGraph InPut(ALGraph G)

    int i;
    char haha[4];
    printf("请输入图的顶点数:");
    scanf("%d",&G.vexnum);
    printf("请输入图的所有顶点信息(如:v1 v2 v3):");
    for(i=0;i<G.vexnum;i++)
    
        scanf("%s",G.adjList[i].vertex);
        G.adjList[i].link=NULL;
    
    printf("请输入图的边数:");
    scanf("%d",&G.arcnum);
    printf("请输入图的所有边信息(如:v1,v2 v1,v3):\\n");
    for(i=0;i<G.arcnum;i++)
    
        scanf("%s",G.bian[i].one);
        scanf("%s",G.bian[i].two);
        gets(haha);
    
    printf("输入完毕\\n\\n");
    return G;

//构成节点
void Jiedian(int n,int n1,ALGraph &G)

    ArcNode *p,*q;
    if(G.adjList[n].link==NULL)
    
        q=(ArcNode *)malloc(sizeof(ArcNode));        //开辟 节点 空间
        if(!q)                                        //判断开辟节点 是否 成功
        
            printf("节点生成错误!返回主函数\\n");
            return;
        
        q->adjvex=n1;            //节点数据赋值
        q->next=NULL;
        G.adjList[n].link=q;
    
    else
    
        p=G.adjList[n].link;
        q=(ArcNode *)malloc(sizeof(ArcNode));        //开辟 节点 空间
        if(!q)            //判断开辟节点 是否 成功
        
            printf("节点生成错误!返回主函数\\n");
            return;
        
        q->adjvex=n1;
        q->next=NULL;
        if(p->next==NULL)
        
            if(p->adjvex<q->adjvex)
            
                p->next=q;
            
            else
            
                G.adjList[n].link=q;
                q->next=p;
                p->next=NULL;
            
        
        else
        
            if(p->adjvex>q->adjvex)
            
                q->next=p;
                G.adjList[n].link=q;                
            
            else
            
                while(p->next)
                
                    if(p->next->adjvex>q->adjvex)
                    
                        q->next=p->next;
                        p->next=q;
                        break;
                    
                    p=p->next;
                
                if(p->next==NULL)
                    p->next=q;
            
        
    
    

//构成图的邻接表存储结构
void CreateMGraph(ALGraph &G)

    int i,one1,two1;
    for(i=0;i<G.arcnum;i++)
    
        one1=PanDuan(G.bian[i].one,G);            //调用 函数
        two1=PanDuan(G.bian[i].two,G);            //调用 函数
        Jiedian(one1,two1,G);                //调用 函数
        Jiedian(two1,one1,G);                //调用 函数
    
    printf("图的邻接表构成完毕!\\n\\n");

//输出图的邻接表存储信息
void OutPutMGraph(ALGraph &G)

    ArcNode *p;
    for(int i=0;i<G.vexnum;i++)
    
        p=G.adjList[i].link;
        printf("%d|%s|",i,G.adjList[i].vertex);
        while(p)
        
            printf("-->|%d|",p->adjvex);
            p=p->next;
        
        if(p==NULL)
            printf("-->NULL\\n");
    
    printf("图的邻接表输出完毕!\\n\\n");

//输出图的深度优先遍历顺序
void DFS(int i,ALGraph &G)            //图的深度优先遍历的递归运算

    printf("%s ",G.adjList[i].vertex);
    visit[i]=1;
    ArcNode *p;
    p=G.adjList[i].link;
    while(p!=NULL)
    
        if(G.adjList[i].link&&!visit[p->adjvex])
        
            DFS(p->adjvex,G);
        
        p=p->next;
    

void DFStraversal(ALGraph &G)

    char haha[5];
    printf("请输入开始遍历的第一个结点向量: ");
    scanf("%s",haha);                            //输入  第一个 开始 遍历的节点
    printf("深度优先遍历的结果为:");
    for(int i=0;i<G.vexnum;i++)                    //这个for循环 是寻找 第一个开始 遍历的节点
    
        if(strcmp(G.adjList[i].vertex,haha)==0)            //判断字符串 是否 相等
        
            DFS(i,G);            //从 用户 输入的第一个 节点开始 遍历
            break;
        
    
    for(i=0;i<G.vexnum;i++)            //把 没有 输出来的 节点 输出来
    
        if(visit[i]==0)            //判断 当前节点 是否已经 输出来了
        
            DFS(i,G);      //没输出来的 节点 调用 DFS递归函数  
        
    
    printf("\\n遍历完毕\\n\\n");

//退出
void TuiChu()

    printf("~谢谢使用~\\n");

//主函数
int main()

    int choice;
    ALGraph G;
    while(true)                                //无限 使用 本程序
    
        printf("********欢迎使用图的深度优先遍历程序********\\n");   //用户界面
        printf("*****输入图的相关信息          请输入 1*****\\n");
        printf("*****构成图的邻接表存储结构    请输入 2*****\\n");
        printf("*****输出图的邻接表存储信息    请输入 3*****\\n");
        printf("*****输出图的深度优先遍历顺序  请输入 4*****\\n");
        printf("*****退出                      请输入 0*****\\n");
        printf("请输入您的选择:");
        scanf("%d",&choice);
        if(choice>4||choice<0)                //异常判断   不要这个 也行
        
            printf("请输入0~4之间的数字!请重新输入!\\n\\n");
            continue;
        
        switch(choice)            //选择哪一个操作
        
        case 1:        G=InPut(G);
            break;
        case 2:        CreateMGraph(G);
            break;
        case 3:        OutPutMGraph(G);
            break;
        case 4:        DFStraversal(G);
            break;
        case 0:        TuiChu();
            exit(0);
        
    
    return 0;


6.测试结果

6.1输入部分用户界面


图 6.1 输入部分用户界面

6.2生成邻接表用户界面


图 6.2生成邻接表用户界面

6.3输出邻接表信息用户界面


图 6.3输出邻接表信息用户界面

 

6.4深度优先遍历用户界面


图 6.4深度优先遍历用户界面

 

6.5退出部分用户界面


图 6.5退出部分用户界面



以上是关于图的深度优先遍历-C语言实现的主要内容,如果未能解决你的问题,请参考以下文章

C语言实现图的广度优先搜索遍历算法

图的深度优先遍历-C语言实现

超详细C语言版数据结构:图的深度优先遍历(推荐收藏)

超详细C语言版数据结构:图的深度优先遍历(推荐收藏)

超详细C语言版数据结构:图的深度优先遍历(推荐收藏)

超详细C语言版数据结构:图的深度优先遍历(推荐收藏)