数据结构图的基本操作.docx
- 文档编号:10645271
- 上传时间:2023-02-22
- 格式:DOCX
- 页数:24
- 大小:19.04KB
数据结构图的基本操作.docx
《数据结构图的基本操作.docx》由会员分享,可在线阅读,更多相关《数据结构图的基本操作.docx(24页珍藏版)》请在冰豆网上搜索。
数据结构图的基本操作
数据结构---图的基本操作
#include"stdio.h"
#include"malloc.h"
#defineMAX_VERTEX_NUM20
#defineOK1
#defineerror-1
#defineERROR0
#defineErrorInput-2
typedefintVertexType;
typedefintStatus;
intCHIOCE;//用来接收用户的选择
intVEXNUM,ARCNUM;//用来接收用户输入的顶点和弧数目
inti;
typedefstructArcNode
{
intadjvex;//该弧所指向的顶点的位置
structArcNode*nextarc;//指向下一条弧的指针
//InfoType*info;//相关信息
}ArcNode;
typedefstructVNode
{
VertexTypedata;//顶点信息(可放权值)
ArcNode*firstarc;//指向第一条依附该顶点的弧的指针
}VNode,AdjList[MAX_VERTEX_NUM];
typedefstruct
{
AdjListvertices;
intvexnum,arcnum;//vexcount;//图的当前顶点和弧数和顶点计数,count记录真实结点个数
intkind;//图的种类
}ALGraph;
typedefintElemType;
#defineNULL0
typedefintElemType;
typedefstructQNode
{
ElemTypedata;
structQNode*next;
}QNode,*QueuePtr;
typedefstruct
{
QueuePtrfront;
QueuePtrrear;
}LinkQueue;
boolInitQueue(LinkQueue&Q)
{
Q.front=Q.rear=(QueuePtr)malloc(sizeof(QNode));
if(!
Q.front)returnfalse;
Q.front->next=NULL;
returntrue;
}
boolDestroyQueue(LinkQueue&Q)
{
while(Q.front)
{
Q.rear=Q.front->next;
free(Q.front);
Q.front=Q.rear;
}
returntrue;
}
boolEnQueue(LinkQueue&Q,ElemTypedata)
{
QueuePtrp;
p=(QueuePtr)malloc(sizeof(QNode));
if(!
p)returnfalse;
p->data=data;
p->next=NULL;
Q.rear->next=p;
Q.rear=p;
returntrue;
}
boolDeQueue(LinkQueue&Q,ElemType&data)
{
QueuePtrp;
if(Q.front==Q.rear)returnfalse;
p=Q.front->next;
data=p->data;
Q.front->next=p->next;
if(Q.rear==p)Q.rear=Q.front;
free(p);
returntrue;
}
boolGetQueueTop(LinkQueueQ,ElemType&data)
{
if(Q.front==Q.rear)returnfalse;
data=(Q.front->next)->data;
returntrue;
}
boolQueueEmpty(LinkQueue&Q)
{
if(Q.front==Q.rear)returntrue;
returnfalse;
}
voidInitiateGraph(ALGraph*G)
{
inti;
G->vexnum=0;
G->arcnum=0;
for(i=0;i { G->vertices[i].firstarc=NULL; } } /**********************在图G中第i个位置增添新顶点v*****************/ voidInsertVex(ALGraph*G,inti,VertexTypev) { if(i>=0&&i { G->vertices[i].data=v;//存储顶点数据元素vextex G->vexnum++;//个数加1 } else printf("顶点越界\n"); } /***************************在图G中删除v*************************/ StatusDeleteVex(ALGraph&G,intv) {//(事实上只是释放V-1处的空间并对v-1.data=-2做标记) inti=0; ArcNode*p,*q; for(i=0;i { if(i==v)continue; if(G.vertices[i].firstarc==NULL)continue; if(G.vertices[i].firstarc->adjvex==v) //如果v为该节点的第一个临界弧所指向的顶点位置 { p=G.vertices[i].firstarc; G.vertices[i].firstarc=p->nextarc; free(p); G.arcnum--; } else {//q用来记录前一个弧,p为当前弧 for(p=G.vertices[i].firstarc;p! =NULL;q=p,p=p->nextarc) { if(p->adjvex==v) { q->nextarc=p->nextarc; free(p); G.arcnum--; break;//弧只有一条所以用break跳出 } } } } //*********************删除以v为弧尾的边*************** if(G.vertices[v].firstarc! =NULL) { p=G.vertices[v].firstarc; //p记录前一个弧 q=p->nextarc; //q为当前弧 //G.vertices[v].firstarc=NULL; while (1) { free(p); G.arcnum--; if(q==NULL) { break; } else { p=q; q=q->nextarc; } } } /*********************从数组中删除v节点**************************/ for(i=v;i G.vertices[i]=G.vertices[i+1]; G.vexnum--; returnOK; } voidConnect(ALGraph&G,intv,intw) { ArcNode*p,*q; if(G.vertices[v].firstarc==NULL) {//如果是第一个节点为NULL,则直接建立 p=(ArcNode*)malloc(sizeof(ArcNode)); p->adjvex=w; p->nextarc=NULL; G.vertices[v].firstarc=p; } else {//如果不是NULL则进行遍历到最后一个弧 for(p=G.vertices[v].firstarc;p! =NULL;q=p,p=p->nextarc); p=(ArcNode*)malloc(sizeof(ArcNode)); p->adjvex=w; p->nextarc=NULL; q->nextarc=p; } } /*****在G中增添弧 intInsertArc(ALGraph&G,intv,intw) { if(v<0||v>=G.vexnum||w<0||w>=G.vexnum) { printf("参数错误\n"); return0; } else { Connect(G,v,w); G.arcnum++; if(G.kind==1) {//如果是无向图则反向插入一个弧 Connect(G,w,v); G.arcnum++; } printf("添加弧成功\n"); return1; } } /*******************删除节点v和w间的弧***********************************/ StatusDelete(ALGraph&G,intv,intw) { ArcNode*p,*q; if(G.vertices[v].firstarc->adjvex==(w)) //该弧是第一条依附顶点v的弧 { p=G.vertices[v].firstarc; G.vertices[v].firstarc=p->nextarc; free(p); G.arcnum--; returnOK; } else { //否则遍历找到这条弧 for(p=G.vertices[v].firstarc;(p->adjvex! =w)&&(p->nextarc! =NULL);q=p,p=p->nextarc); if(p->adjvex==w) { q->nextarc=p->nextarc; free(p); G.arcnum--; returnERROR; } else printf("该弧不存在");returnOK; } } /*****在G中删除弧 StatusDeleteArc(ALGraph&G,intv,intw) { if(v<0||v>G.arcnum||w<0||w>G.arcnum) { printf("参数错误"); returnERROR; } else { Delete(G,v,w); if(G.kind==1) { Delete(G,w,v); } returnOK; } } /***********若G中存在顶点u,则返回该顶点在图中位置;否//则返回其它信息*******/ intLocateVex(ALGraphG,intu) { inti=0; while((G.vertices[i].data! =u)&&(i //遍历数组G.vertices[]查找u i++; if(G.vertices[i].data==u) returni; else returnERROR; } /***********返回v的值*******************************/ intGetVex(ALGraphG,intv) { if(v<0||v>G.arcnum) { printf("参数错误"); returnERROR; } else returnG.vertices[v].data; } //**********对v赋值value******************************* StatusSetVex(ALGraph&G,intv,intval) { if(v<0||v>G.arcnum) { printf("参数错误"); returnERROR; } else { G.vertices[v].data=val; returnOK; } } //******返回v的第一个邻接点。 若该顶点在G中没有邻//接点,//则返回-1****** intFirstAdjVex(ALGraphG,intv) { if(v<0||v>G.arcnum) { printf("参数错误"); returnERROR; } else { if(G.vertices[v].firstarc! =NULL) returnG.vertices[v].firstarc->adjvex; else { //printf("来自FirstAdjVex函数: 顶点: %d没有邻接顶点\n",v); returnerror; } } } //返回v的(相对于w的)下一个邻接点。 若w是v的最后一个邻接点,则返回"空"。 ** intNextAdjVex(ALGraph&G,intv,intw) { ArcNode*p; if(v>G.vexnum||w>G.vexnum) returnErrorInput;//输入值不正确返回-2 p=G.vertices[v].firstarc; while(p! =NULL) { if(p->adjvex! =w) { p=p->nextarc; continue; } else break; } if(p==NULL) { //printf("w不是v的邻接顶点"); returnerror; } else { if(p->nextarc! =NULL) return(p->nextarc->adjvex); else { //printf("v邻接顶点w的下一个邻接顶点不存在"); returnerror; } } } //**************创建图函数************************** StatusCreateALG(ALGraph&G) { ALGraph*Gpointer=&G; inti=0; intout,in; printf("请输入顶点(Vex)个数: "); scanf("%d",&VEXNUM); //G.vexcount=G.vexnum; printf("请输入弧(Arc)数: "); scanf("%d",&ARCNUM); printf("请输入图的类型(0-有向图,1-无向图): "); scanf("%d",&G.kind); InitiateGraph(Gpointer); //int*intarray=newint[G.vexnum]; for(i=0;i { InsertVex(Gpointer,i,i+1); //G.vertices[i].data=i+1; //G.vertices[i].firstarc=NULL; } for(i=0;i { printf("请输入弧(outint): "); scanf("%d%d",&out,&in); if(! InsertArc(G,out,in)) { i--; } } //if(G.kind==1)G.arcnum*=2; returnOK; } //**************从顶点v起深度优先遍历图G************** boolvisited[20]; voidDFS(ALGraphG,intv) { intw; visited[v]=true;//访问第v个顶点 printf("%d\t%d\n",v,G.vertices[v].data); for(w=FirstAdjVex(G,v);w>=0;w=NextAdjVex(G,v,w)) { if(! visited[w])DFS(G,w);//对v的为访问的邻接顶点w递归调用DFS } } voidDFSTraverse(ALGraphG) { for(i=0;i { if(G.vertices[i].data<0) { visited[i]=true; } visited[i]=false; } printf("位置\t数据\t\n"); for(i=0;i { if(! visited[i])DFS(G,i); } } //****************从顶点v起广度优先遍历图G*********** voidBFSTraverse(ALGraphG) { intw=0; for(i=0;i { if(G.vertices[i].data<0) { visited[i]=true; } visited[i]=false; } LinkQueueQ; InitQueue(Q); printf("位置\t数据\t\n"); for(i=0;i { if(! visited[i]) { visited[i]=true; printf("%d\t%d\n",i,G.vertices[i].data); EnQueue(Q,i); while(! QueueEmpty(Q)) { DeQueue(Q,i); for(w=FirstAdjVex(G,i);w>=0;w=NextAdjVex(G,i,w)) { if(! visited[w]) { visited[w]=true; printf("%d\t%d\n",w,G.vertices[w].data); EnQueue(Q,w); } } } } } DestroyQueue(Q); } StatusDestroyGraph(ALGraph&G) { intv=0; for(v=0;v { DeleteVex(G,v+1); } returnOK; } StatusPrintGraph(ALGraphG) { ArcNode*p; inti=0; printf("位置\t数据\t顶点"); for(i=0;i { if(G.vertices[i].data<0) { continue; } printf("%d\t",i); printf("%d\t",G.vertices[i].data); if(G.vertices[i].firstarc! =NULL) { for(p=G.vertices[i].firstarc;p! =NULL;p=p->nextarc) { printf("%d\t",p->adjvex); } } printf("\n"); } returnOK; } voidmain() { intv,w,next; ALGraphG;ALGraph*Gpointer=&G; puts("---------建立图-----------"); CreateALG(G); PrintGraph(G); printf("执行退出操作请输入0\n"); printf("执行插入顶点操作请输入1\n"); printf("执行删除顶点操作请输入2\n"); printf("执行插入弧操作请输入3\n"); printf("执行删除弧操作请输入4\n"); printf("执行查找顶点位置操作请输入5\n"); printf("执行查找某位置顶点的值操作请输入6\n"); printf("执行对某顶点赋值操作请输入7\n"); printf("执行返回v的第一个邻接点操作请输入8\n"); printf("执行返回v的(相对于w的)下一个邻接点,请输入零度摆渡KingEasternSun9\n"); printf("执行从顶点v起深度优先遍历图操作请输入10\n"); printf("执行从顶点v起广度优先遍历图操作请输入11\n"); printf("请输入命令: "); scanf("%d",&CHIOCE); while(CHIOCE! =0) { switch(CHIOCE) { case1: //插入顶点 printf("请输入要插入顶点的值\n"); scanf("%d",&v); InsertVex(Gpointer,G.vexnum,v); PrintGraph(G); printf("+++++++++++++++++++++++++++++++++\n");break; case2: //删除顶点 printf("请输入要删除顶点的位置\n"); scanf("%d",&v); DeleteVex(G,v); PrintGraph(G); printf("+++++++++++++++++++++++++++++++++\n");break; case3: printf("请输入要插入弧的两端顶点顶点\n"); printf("请输入弧outint): ");
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 数据 结构图 基本 操作