用邻接表表示图

邻接表图的常用储存结构之一,由表头结点和表结点两部分组成,其中表头结点存储图的各顶点,表结点用单向链表存储表头结点所对应顶点的相邻顶点(也就是表示了图的边)。在有向图里表示表头结点指向其它结点(a->b),无向图则表示与表头结点相邻的所有结点(a—b)

以一个无向图为例


结构定义:

//表头结点(表示图的顶点)
struct vnode{
       char data;             //顶点数据,这里用字符表示
       struct arcnode * firstarc;   //指针指向第一条边 
};
//表结点(表示图的边)
struct arcnode{
       int wt;           //权重
       int adjvex;     //顶点下标
       struct arcnode *nextarc;   //指针指向下一条边
};
typedef struct arcnode * Arc;
//图
struct mgraph{
       struct vnode vexs[100];
       int vexsnum,arcnum;     //顶点数,边数
} *g;
typedef struct mgraph* Graph;

建图并输出图

int findadj(char vexs,Graph g){
	int i;
	for(i=1;i<=g->vexsnum;i++){
		if(vexs==g->vexs[i].data)
			break;
	}
	return i;  
}

//建图
Graph creategraph(){
	      Graph g1;
          char vex;
          g1=(Graph)malloc(sizeof(struct mgraph));
          g1->arcnum=0;
          g1->vexsnum=0;
		  printf("输入顶点,输入-代表结束\n");
		  scanf("%c",&vex);    //输入顶点
		  while(vex!='-'){         //输入-后循环结束
			  g1->vexsnum++;
			  g1->vexs[g1->vexsnum].data=vex;      //这里的结构数组vexs[]下标从1开始
			  g1->vexs[g1->vexsnum].firstarc=NULL;
			  printf("输入下一个顶点,输入-代表结束\n");
		      scanf(" %c",&vex);         //%c前面加空格防止读取回车
		  }
		  int i;
		  int w;           //边的权重
		  int adjvex;    //顶点的下标
		  char avex;    //边的另一个顶点
		  Arc p,b;
		  for(i=1;i<=g1->vexsnum;i++){
			  printf("输入%c的相邻顶点,输入-代表结束",g1->vexs[i].data);
			  scanf(" %c",&avex);
			  while(avex!='-'){    //输入-后循环结束
			      adjvex=findadj(avex,g1);
				  printf("输入边%c%c的权重\n",g1->vexs[i].data,avex);
				  scanf("%d",&w);
				  b=(Arc)malloc(sizeof(struct arcnode));
				  b->adjvex=adjvex;
				  b->wt=w;
				  b->nextarc=NULL;
				  //链表追加结点
				  p=g1->vexs[i].firstarc;
				  if(p!=NULL){
					  while(p->nextarc!=NULL)
						  p=p->nextarc;
					  p->nextarc=b;
				  }else
					  g1->vexs[i].firstarc=b;
				  g1->arcnum++;        
				  printf("输入%c的相邻顶点,输入-代表结束",g1->vexs[i].data);
				  scanf(" %c",&avex);
			   }
		  }
	  return g1;
}

//图的输出
void printgraph(Graph g){
	int i,k;
	Arc p;
	printf("———邻接表————\n");
	for(i=1;i<=g->vexsnum;i++){
		printf("%c  ->",g->vexs[i].data);
		p=g->vexs[i].firstarc;
		while(p!=NULL){
			printf("%4c",g->vexs[i].data);
			k=p->adjvex;
			printf("%2c",g->vexs[k].data);
			printf("%2d",p->wt);
			if(p->nextarc!=NULL)
			printf("  ->");
			p=p->nextarc;
		}
		printf("\n");
	}
	printf("\n");
    printf("—————————\n");
	printf("顶点总数为%4d\n",g->vexsnum);
	printf("边的总数为%4d\n",g->arcnum);
}

void main(){
	 g=creategraph();
	 printgraph(g);
}


控制台输出



  • 15
    点赞
  • 63
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值