以邻接链表的方式确定一个无向网

发布时间:2024-11-08 02:39 发布:上海旅游网

问题描述:

以邻接链表的方式确定一个无向网 请完成:
⑴建立并显示出它的邻接矩阵;
⑵对该图进行广度优先遍历,显示遍历的结果,(并随时显示队列的入、出情况);
⑶用普里姆算法构造其最小生成树,随时显示其构造的过程;
这是数据结构的课程设计,拜托哪位高手帮帮忙啊,我只有这么多分,拜托了

问题解答:

#include <iostream>
#include <stdio.h>
#include <string>
using namespace std;
#define max 10

class node_shuzu;
//邻接链表链结点
class node_lianbiao
{
public:
int position;
int quanzhi;
node_lianbiao * next;

node_lianbiao(int a,int b){position=a;quanzhi=b; next=NULL;}
node_lianbiao(){next=NULL;}
~node_lianbiao(){}
};
//邻接链表数组结点
class node_shuzu
{
public:
node_lianbiao *next;
string data;

node_shuzu(){next=NULL;}
~node_shuzu(){}
};
//图类
class tu_juzhen
{
private:
int juzhen[max][max];
string dingdian[max];
int numding,numhu;
node_shuzu lianbiao[max];
public:
tu_juzhen(){}
void creat();
int locateding( string );//返回这个顶点的第几位
int isempty();//判断是否为空
void guangdubianli();
void printgragh();
void prim();
void ktus();
};

int tu_juzhen::locateding(string b)
{
int i=0;
for(;i<numding;i++)
{
if(dingdian[i]==b) return i;
}
return -1;
}

void tu_juzhen::creat()
{
string data,data1,data2;
int n,m,num;
//输入顶点个数
cout<<"请输入顶点个数:";
cin>>numding;
//输入顶点
cout<<"请依次输入各个顶点:";
for(int i=0;i<numding;i++)
{
cin>>dingdian[i];
}
//以邻接链表确定有向网
node_lianbiao * * po[max];//指向数组链表的最后一位的next成员

for (int i=0;i<numding;i++)
{lianbiao[i].data=dingdian[i];po[i]=&lianbiao[i].next;}

cout<<"输入所有的弧,格式为:“顶点顶点权值”,以格式 0 0 0结束"<<endl;
do
{

cin>>data1>>data2>>num;
n=locateding(data1);
m=locateding(data2);
//node_lianbiao a(m,num);
if((n!=-1)&&(m!=-1))
{
*po[n]=new node_lianbiao(m,num);
po[n]=&((*po[n])->next);
*po[m]=new node_lianbiao(n,num);
po[m]=&((*po[m])->next);
}
}
while((data1!="0")&&(data2!="0")&&(num!=0));

//根据邻接链表建立邻接矩阵
node_lianbiao * po1;

for (int i=0;i<numding;i++)//初始化
for (int j=0;j<numding;j++)
juzhen[i][j]=0;

for(int i=0;i<numding;i++)
{
po1=lianbiao[i].next;
while(po1)
{
n=po1->position;
m=po1->quanzhi;
po1=po1->next;
juzhen[i][n]=m;
};
}
}

void tu_juzhen::printgragh()//打印有向网的邻接矩阵
{
cout<<endl;
cout<<"邻接矩阵为:"<<endl;
int i,j;
for(i=0;i<numding;i++)
{
for(j=0;j<numding;j++)
{
cout<<juzhen[i][j]<<" ";
}
cout<<endl;
}
}

void tu_juzhen::guangdubianli()
{
int * flag =new int[numding];//记录顶点访问状态
int * duilie =new int[numding];//记录未广度遍历的顶点数
int front,rear;
front=0;rear=0;
int i;
cout<<endl;
cout<<"该图的广度优先遍历为:"<<endl;
for( i=0;i<numding;i++)flag[i]=0;//状态初始化

do
{
for( i=0;i<numding;i++)if(flag[i]==0)break;
if(i!=numding)
{
cout<<"-->"<<dingdian[i]<<endl;
rear++;
duilie[rear]=i;
cout<<"入队列"<<dingdian[i]<<endl;
flag[i]=1;
do
{
cout<<"出队列"<<dingdian[duilie[front+1]]<<endl;
front=(front+1)%20;
for(int j=0;j<numding;j++)
{
if((juzhen[duilie[front]][j]!=0)* (flag[j]!=1))
{
rear++;
duilie[rear]=j;
cout<<"入队列"<<dingdian[j]<<endl;
flag[j]=1;
cout<<"-->"<<dingdian[j]<<endl;
}
}
}
while((((rear+1)%20)!=front) * (rear!=front));//队列结束条件。队列满或空
}
}
while(i!=numding);
cout<<endl;
}

void tu_juzhen::prim()
{
int flag[max],dian[max],n,m,l,p=0;//flag[]标志结点所属树,p表示已写出结点个数

int juzhen1[max][max];//矩阵的映像
for(int i=0;i<numding;i++)
for (int j=0;j<numding;j++)
juzhen1[i][j]=juzhen[i][j];
for(int i=0;i<numding;i++)flag[i]=0;//初始化

cout<<"普里姆算法"<<endl;
//先找到最小的一个弧
l=n=m=10000;//假设一个很大值
for(int i=0;i<numding;i++)
for (int j=i;j<numding;j++)
{
if((juzhen1[i][j]!=0)&&(juzhen1[i][j]<l))
{
l=juzhen1[i][j];
m=i;n=j;
}
}
p+=2;dian[0]=m;dian[1]=n;flag[n]=flag[m]=1;
cout<<dingdian[n]<<"与顶点"<<dingdian[m]<<"相连 权值为"<<l<<endl;

while(p<numding)
{
l=n=m=10000;
for(int i=0;i<p;i++)
{
for (int j=0;j<numding;j++)
{
if((juzhen1[j][dian[i]]!=0)&&(juzhen1[j][dian[i]]<l)&&(flag[j]==0))
{
l=juzhen1[j][dian[i]];
n=dian[i];m=j;
}
}
}
if((m!=10000)&&(n!=10000)&&(l!=10000))
{
dian[p]=m;
p++;
cout<<dingdian[n]<<"与顶点"<<dingdian[m]<<"相连 权值为"<<l<<endl;

flag[m]=1;
}
}
cout<<endl;
}

void tu_juzhen::ktus()
{
int flag[max],n,m,l,p,k;//flag[]标志结点所属树,p表示已写出弧个数

int juzhen1[max][max];//矩阵的映像
for(int i=0;i<numding;i++)
for (int j=0;j<numding;j++)
juzhen1[i][j]=juzhen[i][j];

cout<<"克鲁斯卡尔算法:"<<endl;

for(int i=0;i<numding;i++)flag[i]=0;//初始化
k=p=0;
while (p<(numding-1))
{
l=n=m=10000;//假设一个很大值

for(int i=0;i<numding;i++)
for (int j=0;j<numding;j++)
{
if((juzhen1[i][j]!=0)&&(juzhen1[i][j]<l))
{
l=juzhen1[i][j];
m=i;n=j;
}
}

if((m!=10000)&&(n!=10000)&&(l!=10000))
{
if(flag[n]!=0)
if(flag[m]!=0)
if(flag[n]==flag[m]) //成环情况
{continue;}
else
{
cout<<dingdian[n]<<"与顶点"<<dingdian[m]<<"相连 权值为"<<l<<endl;
p++;
flag[numding]=flag[m];
for(int h=0;h<numding;h++)
if(flag[h]==flag[numding])
flag[h]=flag[n];
}
else
{cout<<dingdian[n]<<"与顶点"<<dingdian[m]<<"相连 权值为"<<l<<endl;flag[m]=flag[n];p++;}//后结点为新
else
if(flag[m]!=0)
{cout<<dingdian[n]<<"与顶点"<<dingdian[m]<<"相连 权值为"<<l<<endl;flag[n]=flag[m];p++;}//前结点为新
else
{cout<<dingdian[n]<<"与顶点"<<dingdian[m]<<"相连 权值为"<<l<<endl;flag[n]=flag[m]=k;p++;}//前后结点均为新

juzhen1[m][n]=juzhen1[n][m]=0;
}
k++;

};
cout<<endl;
}
void main()
{
tu_juzhen li;
li.creat();
li.printgragh();
li.guangdubianli();

li.ktus();
li.prim();

}

热点新闻