图的实验报告 遍历演示
院系:数学与统计学学院专业:统计学
年级: 2008级
课程名称:数据结构
学号: 08067041 姓名:刘玉芝
指导教师:强小利
2010年 12 月 8日
年级2008级
班号
02
学号 08067041
专
业
统计学姓名刘玉芝实
验名称图的遍历演示
实验
类型
设计
型
综合
型
创新型
√
实验
目的或要求要求:
1 图采用领接表的存储结构
2 深度优先搜索图
3 广度优先搜索图
实验原理(算法流程)#include
#include
#define MAX_VERTEX_NUM 20
#define STACK_INIT_SIZE 100
#define STACKINCREMENT 10
#define TRUE 1
#define OK 1
#define FALSE 0
#define ERROR 0
#define OVERFLOW -2
typedef enum{DG,DN,UDG,UDN}GraphKind;//{有向图,有向网,无向图,无向网} bool visited[MAX_VERTEX_NUM];
typedef struct ArcNode
{
int adjvex;//该弧所指向的顶点在数组中的下标
struct ArcNode *nextarc;
int *info;//该弧相关信息的指针
}ArcNode;
typedef struct VNode
{
int data;//顶点信息
ArcNode *firstarc;//指向第一条依附该顶点的弧的指针
}VNode,AdjList[MAX_VERTEX_NUM];
typedef struct
{
AdjList vertices;
int vexnum,arcnum;//图的当前顶点数和弧数
int kind;//图的种类标志
}ALGraph;
typedef struct
{
int *base;
int *top;
int stacksize;
}SqStack;
typedef struct QNode
{
int data;
struct QNode *next;
}QNode,*QueuePtr;
typedef struct
{
QueuePtr front;
QueuePtr rear;
}LinkQueue;
int LocateV ex(ALGraph G,int v)
{//返回数组下标值
int i;
for(i=0;i if(G.vertices[i].data==v) return i; return -1; } void CreateDN(ALGraph &G) {//采用邻接表存储表示,构造有向图G(G.kind=DN) int i,j,k;ArcNode *p;int v1,v2; G.kind=DN; printf(" 输入顶点数:"); scanf("%d",&G.vexnum); printf(" 输入弧数:"); scanf("%d",&G.arcnum); printf(" 输入顶点:\n"); for(i=0;i {//构造表头向量 scanf("%d",&G.vertices[i].data); G.vertices[i].firstarc=NULL;//初始化指针 } for(k=0;k { printf("第%d条弧: ",k+1); scanf("%d",&v1); scanf("%d",&v2);//输入一条弧的始点和终点 i=LocateV ex(G,v1);j=LocateV ex(G,v2);//确定v1和v2在G中位置 p=(ArcNode*)malloc(sizeof(ArcNode));//假定有足够空间 p->adjvex=j;p->nextarc=G.vertices[i].firstarc; G.vertices[i].firstarc=p; scanf("%d",&p->info); }//for } int Push(SqStack &S,int e) {//插入元素e为新的栈顶元素 if(S.top-S.base>=S.stacksize) {//栈满,追加存储空间 S.base=(int*)realloc(S.base,(S.stacksize+STACKINCREMENT)*sizeof(int)); if(!S.base)exit(OVERFLOW); //存储分配失败 S.top=S.base+S.stacksize; S.stacksize+=STACKINCREMENT; } *S.top++=e; return OK; } int InitStack(SqStack &S) //栈的初始化 { S.base=(int*)malloc(STACK_INIT_SIZE*sizeof(int)); if(!S.base)exit(OVERFLOW); //存储分配失败 S.top=S.base; S.stacksize=STACK_INIT_SIZE; return OK; } int Pop(SqStack &S,int &e) //删除栈顶元素 {//若栈不空,则删除S的栈顶元素,用e返回其值 if(S.top==S.base) return ERROR; e=*--S.top; return OK; } int GetTop(SqStack S,int &e) //取栈顶元素 {//若栈不空,则用e返回S的栈顶元素 if(S.top==S.base) return ERROR; e=*(S.top-1); return OK; } int StackEmpty(SqStack S) //栈空 { if(S.top==S.base) return TRUE; else return FALSE; } int InitQueue(LinkQueue &Q) //队列初始化 { Q.front=Q.rear=(QueuePtr)malloc(sizeof(QNode)); if(!Q.front)exit(OVERFLOW); Q.front->next=NULL; return OK; } int EnQueue(LinkQueue &Q,int e) //插入 {//插入元素e为Q的新的队尾元素 QueuePtr p=(QueuePtr)malloc(sizeof(QNode)); if(!p)exit(OVERFLOW); p->data=e;p->next=NULL; Q.rear->next=p; Q.rear=p; return OK; } int DeQueue(LinkQueue &Q,int &e) {若队列不空,则删除Q的队头元素,用e返回其值if(Q.front==Q.rear) return ERROR; QueuePtr p=Q.front->next; e=p->data; Q.front->next=p->next; if(Q.rear==p)Q.rear=Q.front; free(p); return OK; } int QueueEmpty(LinkQueue Q) //队列空 { if(Q.front==Q.rear) return TRUE; else return FALSE; } int FirstAdjV ex(ALGraph G,int u) { if(!G.vertices[u].firstarc) return -1; return LocateV ex(G,G.vertices[u].firstarc->adjvex); } int NextAdjV ex(ALGraph G,int u,int w) { ArcNode *p=G.vertices[u].firstarc; while(p&&LocateV ex(G,p->adjvex)!=w) p=p->nextarc; if(!p) return FirstAdjV ex(G,u); p=p->nextarc; if(!p) return -1; return LocateV ex(G,p->adjvex); } void Visit(ALGraph G,int v) { printf("%2d",G.vertices[v].data); } void DFSTraverse(ALGraph G) {//按深度优先非递归遍历图G,使用辅助栈S和访问标志数组visited int v,w;SqStack S; for(v=0;v visited[v]=FALSE; InitStack(S); for(v=0;v if(!visited[v]) {//v尚未被访问 visited[v]=TRUE; V isit(G,v); Push(S,v);//v进栈 while(!StackEmpty(S)) { for(w=FirstAdjV ex(G,v);w>=0;w=NextAdjV ex(G,v,w)) { if(!visited[w]) { V isit(G,w); visited[w]=TRUE; Push(S,w); GetTop(S,v); }//if }//for Pop(S,v); GetTop(S,v); }//while }//if printf("\n"); } void BFSTraverse(ALGraph G) {//按广度优先非递归遍历图G,使用辅助队列Q和访问标志数组visited int v,u,w;LinkQueue Q; for(v=0;v visited[v]=FALSE; InitQueue(Q); for(v=0;v if(!visited[v]) {//v尚未被访问 visited[v]=TRUE; V isit(G,v); EnQueue(Q,v);//v入队列 while(!QueueEmpty(Q)) { DeQueue(Q,u);//队头元素出队并置为u for(w=FirstAdjV ex(G,u);w>=0;w=NextAdjV ex(G,u,w)) if(!visited[w]) {//w为u的尚未访问的邻接顶点 visited[w]=TRUE;Visit(G,w); EnQueue(Q,w); }//if }//while }//if printf("\n"); } void PrintDN(ALGraph G) //图的显示 { int i;ArcNode *p; printf("顶点:\n"); for(i=0;i printf("%2d",G.vertices[i].data); printf("\n弧:\n"); for(i=0;i { p=G.vertices[i].firstarc; if(p) { while(p) { printf("%d→%d(%d)\t",i,p->adjvex,p->info); p=p->nextarc; } printf("\n"); }//if }//for } void main() { ALGraph G; printf("************题目:图的遍历***************\n\n"); CreateDN(G); PrintDN(G); printf(" 深度优先遍历:"); DFSTraverse(G); printf("\n 广度优先遍历:"); BFSTraverse(G); } 组 内 分 工 ( 可 选 ) 8 2 2 1 6 7 3 1 6 4 5 4 3 9 5 7 (所要遍历的图) 主程序 实 验 结 果 分 析 及 心 得 体 会 实验结果 成 绩 评定教师签名: 2010年月日