#include<iostream>
#define NumVertices 10
#define INF 0x3f3f3f3f
#include<algorithm>//归并 归并两个有序序列 merge();min();max();
using namespace std;
typedef char VerTexType;//顶点数据类型char
typedef int ArcType;//边的权值数据类型Int
typedef struct{
VerTexType vexlist[NumVertices];//顶点表
ArcType arc[NumVertices][NumVertices];//邻接矩阵
int n,e;//n顶点个数,e边个数
}AMGragh;
bool isEdge(AMGragh &G,int v1,int v2){
if(v1>=0&&v1<G.n&&v2>=0&&v2<G.n&&v1!=v2){//首先要满足是矩阵里面的点,且不能是同一个点(同一个点怎么构成边!!)
if(G.arc[v1][v2]!=INF)
return true;
else
return false;
}
return false;
}
void setSucc(AMGragh &G,int v1,int v2,int w){
if(isEdge(G,v1,v2))
return;
G.arc[v1][v2]=w;
//G.arc[v2][v1]=w;
G.e++;
}
void CreateAMGragh(AMGragh &G){
int i,j,k,e,weight;
cout<<"输入顶点数和边数:"<<endl;
cin>>G.n>>e;
cout<<"输入顶点字符:"<<endl;
for(i=0;i<G.n;i++)
cin>>G.vexlist[i];//存到顶点表
cout<<"输入一条边的两个顶点下标和权重:"<<endl;
for(i=0;i<G.n;i++)//边初始化为0
for(j=0;j<G.n;j++){
G.arc[i][j]=INF;
}
for(k=0;k<e;k++){
cin>>i>>j>>weight;
setSucc(G,i,j,weight);
//setSucc(G,j,i,weight);
}
}
void PrintAMGragh(AMGragh &G){
cout<<"输出有向图邻接矩阵:"<<endl;
cout<<"\t";
for(int i=0;i<G.n;i++)
{
cout<<G.vexlist[i]<<"\t";
}
cout<<endl;
for(i=0;i<G.n;i++)
{
cout<<G.vexlist[i]<<"\t";
for(int j=0;j<G.n;j++){
if(G.arc[i][j]==INF)
cout<<"∞"<<"\t";
else
cout<<G.arc[i][j]<<"\t";
}
cout<<endl;
}
}
int d[NumVertices][NumVertices];//每对顶点之间的距离
int p[NumVertices][NumVertices];//下标最大的前驱
void iniMatrixDP(AMGragh &G){
for(int i=0;i<G.n;i++)
for(int j=0;j<G.n;j++)
{
d[i][j]=G.arc[i][j];
p[i][j]=-1;
}
}
void floyd(AMGragh &G){
int i,j,k;
for(k=0;k<G.n;k++)
for(i=0;i<G.n;i++)
for(j=0;j<G.n;j++){
if(i==j)
d[i][j]=0;
else{
if(d[i][j]>d[i][k]+d[k][j]){//前提是用INF初始化数组G.arc[i][j]
d[i][j]=d[i][k]+d[k][j];
p[i][j]=k;
}
}
}
}
void printMinPathMatrix(AMGragh &G){
cout<<"输出最短路径矩阵:"<<endl;
cout<<"\t";
for(int i=0;i<G.n;i++)
{
cout<<G.vexlist[i]<<"\t";
}
cout<<endl;
for(i=0;i<G.n;i++){
cout<<G.vexlist[i]<<"\t";
for(int j=0;j<G.n;j++){
if(d[i][j]==INF)
cout<<"∞"<<"\t";
else
cout<<d[i][j]<<"\t";
}
cout<<endl;
}
}
void printPath(AMGragh &G,int u,int v){
cout<<"两点之间的最短路径:";
if(p[u][v]=-1){
if(d[u][v]==INF)
cout<<'<'<<G.vexlist[u]<<','<<G.vexlist[v]<<">为:"<<"∞"<<endl;
else
cout<<'<'<<G.vexlist[u]<<','<<G.vexlist[v]<<">为:"<<d[u][v]<<endl;
return;
}
int k;
k=p[u][v];
printPath(G,u,k);
printPath(G,k,v);
}
void centerPoint(AMGragh &G){
//求偏心度(即最大入度的点),也就是求每一列最大的数
int par[NumVertices],center;
for(int j=0;j<G.n;j++){//列
par[j]=d[0][j];
for(int i=0;i<G.n;i++){//行
if(par[j]<d[i][j])
par[j]=d[i][j];
}
}
//中心点(即最小偏心度)
center=0;//center是顶点下标
for(int i=1;i<G.n;i++)
if(par[i]<par[center])
center=i;
cout<<"\n这个有向图的中心点为:"<<G.vexlist[center]<<endl;
}
void Warshall(AMGragh &G,int a[NumVertices][NumVertices]){
}
void main(){
AMGragh G;
CreateAMGragh(G);
PrintAMGragh(G);
int i;
iniMatrixDP(G);
floyd(G);
printMinPathMatrix(G);
printPath(G,0,3);
printPath(G,2,3);
printPath(G,4,0);
centerPoint(G);
}
/*输入顶点数和边数:
6 10
输入顶点字符:
a b c d e f
输入一条边的两个顶点下标和权重:
0 1 3
0 5 5
0 3 4
1 2 1
1 5 1
2 3 2
3 1 3
4 3 3
4 5 2
5 3 2
*/