图的应用的实验报告.docx
- 文档编号:8439958
- 上传时间:2023-01-31
- 格式:DOCX
- 页数:13
- 大小:64.03KB
图的应用的实验报告.docx
《图的应用的实验报告.docx》由会员分享,可在线阅读,更多相关《图的应用的实验报告.docx(13页珍藏版)》请在冰豆网上搜索。
图的应用的实验报告
实验六图的应用及其实现
一、实验目的
1进一步功固图常用的存储结构。
2•熟练掌握在图的邻接表实现图的基本操作。
3•理解掌握AOV网、A0聊在邻接表上的实现以及解决简单的应用问题
二、实验内容
建立其邻接表存储结构,然
AOV网的类型定义和基本操
[题目一]:
从键盘上输入AOV网的顶点和有向边的信息后对该图拓扑排序,并输出拓扑序列•试设计程序实现上述作,完成上述功能。
测试数据:
教材图7.28
试设计程序实现上述AOE网类型定义和基本操作,完成
[题目二]:
从键盘上输入出其关键路径和关键路径长度。
AOE网的顶点和有向边的信息
建立其邻接表存储结构,输
上述功能。
测试数据:
教材图7.29
三、实验步骤
㈠、数据结构与核心算法的设计描述
基本数据结构:
#defineTRUE1#defineFALSE0#defineOK1#defineERROR0
#defineINFEASIBLE-1
}ArcNode;
typedefstructVNodeII表头结点
{
intdata;II存放顶点信息
structArcNode*firstarc;II指示第一个邻接点
}VNode,AdjList[MAX_VERTEX_NUM];
typedefstruct{II图的结构定义
AdjListvertices;II顶点向量
intvexnum,arcnum;
intIsquan;〃是否含有权值
}MGraph;
typedefstruct
{
int*top;
int*base;
intstacksize;
}Sqstack;
typedefintElemType;
StatusInitstack(Sqstack&s)
{
s.base=(int*)malloc(sizeof(int)*25);
if(!
s.base)
returnERROR;
s.top=s.base;
s.stacksize=25;
returnOK;
}
intindegree[MAX_VERTEX_NUM];
intve[MAX_VERTEX_NUM];//e各顶点的最早发生时间
intvl[MAX_VERTEX_NUM];〃各顶点发生的最晚发生时间
调用的函数
StatusInitstack(Sqstack&s)
StatusPop(Sqstack&s,int&e)
//若栈不空,则删除S的栈顶元素,
//用e返回其值,并返回OK否则返回ERROR
intPush(Sqstack&s,int&e)
intStackEmpty(Sqstacks)//若栈为空栈,则返回TRUE否则返回FLASE
StatusCreateGraph(MGraph&G)
voidDisplay(MGraph&G)/*输出图G的信息*/
voidFindDegree(MGraphg,intindegree[])//对=图中的各个顶点的入度进行统计,并
将第i
//个顶点的入度数放入indegree[i]
intLocateVex(MGraphG,VertexTypeu)
/*初始条件:
图G存在,u和G中顶点有相同特征*/
/*操作结果:
若G中存在顶点u,则返回该顶点在图中位置;否则返回-1*/
StatusToopologicalSort(MGraphg)//对图进行拓扑排序,并输出拓扑排序的结果
StatusToopologicalOrder(MGraphg,Sqstack&T)〃拓扑序列
StatusCriticalPath(MGraphg,SqstackT)//关键路径
㈡、函数调用及主函数设计(可用函数的调用关系图说明)
voidmain(){
MGraphg;
SqstackT;cout«"创建图:
\n";
CreateGraph(g);
cout«"输出图的信息:
\n";
Display(g);
cout«"拓扑排序:
\n";
ToopologicalSort(g);
cout«"求关键历经:
\n";
ToopologicalOrder(g,T);
CriticalPath(g,T);
}
㈢程序调试及运行结果分析
(1)在创建图的过程中需要考虑输入的方便,这就需要标记根据用户选择是否需要输入权值,选择不需要权值时就不会有关权值信息的操作。
所以这就在图的结构体中加ISquan标记(0表示无权值,其他表示有权值)
(2)FindIndegree()函数调用过程就是一个对邻接表遍历的过程,在遍历
过程中需要将弧指向的结点进行入度数组的标记。
便定义了一个Indegree『』数
组。
(3)在求关键路径时,需要两次用到拓扑排序(其中一次是逆拓扑排序),在拓扑排序时还需要注意看看是否有环,若有环则输出提示信息。
㈣实验总结
通过对拓扑排序和求最小路径的操作,首先加强了对图的存储结构和图的遍历的进一步的熟悉和应用,在拓扑排序中还让我们去应用到以前学习的栈的知识,温故的同时也在实践的新的理论。
对图的应用是在生活中应用很广泛,同时图的知识点和算法也是我们这学期学习的精华,例如求关键路径,用到栈,拓扑排序等经典算法,让我们受益匪浅。
四、主要算法流程图及程序清单
1、主要算法流程图:
创建顶点向量的数组
创建了图的邻接表
结束
2、程序清单程序过长,可附主要部分)
#include
#include
#include
#include
#include
#defineTRUE1
#defineFALSE0
#defineOK1#defineERROR0#defineINFEASIBLE-1
typedefintStatus;/*Status
是函数的类型,其值是函数结果状态代码,如
OK等*/
〃定义无穷大
#defineINFINITYINT_MAX#defineMAX_VERTEX_NUM20typedefintVertexType;
typedefintInfoType;
typedefstructArcNode//表结点定义
{
InfoTypeinfo;
intadjvex;//邻接点域,存放与Vi邻接的点在表头数组中的位置
ArcNode*nextarc;//链域,指示依附于vi的下一条边或弧的结点,
}ArcNode;
II表头结点
//存放顶点信息
typedefstructVNode
{intdata;
structArcNode*firstarc;II指示第一个邻接点
}VNode,AdjList[MAX_VERTEX_NUM];
typedefstruct
{II图的结构定义
AdjListvertices;II顶点向量
intvexnum,arcnum;
intIsquan;〃是否含有权值
}MGraph;
intindegree[MAX_VERTEX_NUM];
intve[MAX_VERTEX_NUM];IIe各顶点的最早发生时间
intvl[MAX_VERTEX_NUM];II各顶点发生的最晚发生时间
I*图的邻接表存储(存储结构定义)的基本操作*I
intLocateVex(MGraphG,VertexTypeu)
{
I*初始条件:
图G存在,u和G中顶点有相同特征*I
I*操作结果:
若G中存在顶点u,则返回该顶点在图中位置;否则返回-1*Iinti;
for(i=0;i if(u==G.vertices[i].data) returni; return-1; }; StatusCreateGraph(MGraph&G) {inti,j,k; InfoTypevc; VertexTypeva,vb; ArcNode*p; cout<<"请输入图的顶点数,边数: "; cin>>G.vexnum»G.arcnum; cout<<"请输入"< \n"; for(i=0;i { cin»G.vertices[i].data; G.vertices[i].firstarc=NULL; cout<<"是否含有权值: (若不含权值请输入0,否则输入1)\n"; cin»G.Isquan; if(! G.lsquan) cout<<"请顺序输入每条弧的弧尾弧头"< else cout<<"请顺序输入每条弧的弧尾弧头以及弧的信息(以空格作为间隔): \n"; for(k=0;k { if(! G.Isquan) cin>>va»vb; else cin>>va»vb»vc; i=LocateVex(G,va);/*弧尾*/ j=LocateVex(G,vb);/*弧头*/ p=(ArcNode*)malloc(sizeof(ArcNode));p->adjvex=j; if(G.Isquan) p->info=vc; else p->info=0; p->nextarc=G.vertices[i].firstarc;/*插在表头*/ G.vertices[i].firstarc=p; }returnOK; } voidDisplay(MGraph&G) {/*输出图G的信息*/ inti; ArcNode*p; cout< \n"; for(i=0;i cout< cout< \n"; for(i=0;i { p=G.vertices[i].firstarc; while(p) {cout< p=p->nextarc; 〃system("pause"); } 〃////////////////////////////////////////////////////////////////// // //建立栈相关的数据结构和函数// typedefstruct { int*top; int*base; intstacksize; }Sqstack; typedefintElemType; StatusInitstack(Sqstack&s) {s.base=(int*)malloc(sizeof(int)*25); if(! s.base) returnERROR; s.top=s.base; s.stacksize=25; returnOK; } intPush(Sqstack&s,int&e) {//向栈输入元素 if(s.top-s.base>=s.stacksize) { s.base=(ElemType*)realloc(s.base,(s.stacksize+10)*sizeof(ElemType));if(! s.base)return0; else {s.top=s.base+s.stacksize; s.stacksize+=10; } } *s.top=e; s.top++; returnOK; } StatusPop(Sqstack&s,int&e) { 〃若栈不空,则删除S的栈顶元素, 〃用e返回其值,并返回OK;否则返回ERROR if(s.top==s.base) returnERROR; e=*__s.top; returnOK; }//Pop; intStackEmpty(Sqstacks) { 〃若栈为空栈,则返回TRUE,否则返回FLASE if(s.top==s.base) return1; elsereturn0; } ///////////////////////////////////////////////////////////////////////////// voidFindDegree(MGraphg,intindegree[]) { indegree[i] 〃对=图中的各个顶点的入度进行统计,并将第i个顶点的入度数放入 ArcNode*p; inti; for(i=0;i indegree[i]=0; cout<<"李星运是个SB"< for(intj=0;j for(p=g.vertices[j].firstarc;p! =NULL;p=p->nextarc) indegree[p->adjvex]++; } //对图进行拓扑排序,并输出拓扑排序的结果 StatusToopologicalSort(MGraphg) {Sqstacks; inti; intcount=0; FindDegree(g,indegree); Initstack(s); for(i=0;i if(indegree[i]==0) Push(s,i);〃将入度为0的顶点序号压入零入度栈 while(! StackEmpty(s))〃如果零入度栈中还有结点 {Pop(s,i); cout<<"第"< count++; for(ArcNode*p=g.vertices[i].firstarc;p;p=p->nextarc) {intk=p->adjvex; if(! (--indegree[k])) Push(s,k); } if(countvg.vexnum)〃将结点数与压入零结点栈进行比较{ cout<<"不是连通图! "< returnERROR; } else returnOK; } //拓扑序列 StatusToopologicalOrder(MGraphg,Sqstack&T) { Sqstacks; inti; intcount=0; FindDegree(g,indegree); Initstack(s);//用于存放零入度的结点栈 Initstack(T);//若g不为空,则用T存放柘扑序列 for(i=0;i if(indegree[i]==O)Push(s,i); //初始化数组各结点的最早时间为0 for(i=0;i ve[i]=0; while(! StackEmpty(s)) { Pop(s,i);//将零入度结点栈中的结点弹出一个结点 Push(T,i);〃将弹出的结点序列压入拓扑序列栈T中 count++; for(ArcNode*p=g.vertices[i].firstarc;p;p=p->nextarc){ intk=p->adjvex; if(! (--indegree[k])) Push(s,k);//将入度为0的结点压入零入度栈中if(ve[i]+(p->info)>ve[k]) ve[k]=ve[i]+(p->info); if(countvg.vexnum) returnERROR; else returnOK; } //关键路径 StatusCriticalPath(MGraphg,SqstackT) { inti; ArcNode*p; if(! ToopologicalOrder(g,T)) { cout<<"拓扑排序不成功! \n"; returnERROR; } for(i=0;i vl[i]=ve[i];〃将各顶点的最晚发生时间都赋值为最早发生时间 while(! StackEmpty(T)) for(Pop(T,i),p=g.vertices[i].firstarc;p;p=p->nextarc) { intk=p->adjvex; intdut=p->info; if(vl[k]-dut vl[i]=vl[k]-dut;〃如果顶点的最晚时间大于前一个顶点的最晚时间和其间权 值的差 } for(intj=0;j for(p=g.vertices[i].firstarc;p;p=p->nextarc) {intk=p->adjvex; intdut=p->info; intee=ve[j],el=vl[k]-dut; cout< } returnOK; } voidmain() { MGraphg; SqstackT; cout<<"创建图: \n"; CreateGraph(g);cout<<"各条弧的信息: \n";Display(g); cout<<"拓扑排序: \n"; ToopologicalSort(g);cout<<"求关键历经: \n";ToopologicalOrder(g,T);CriticalPath(g,T); }
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 应用 实验 报告