矩阵乘法求最短路

算法导论矩阵乘法求最短路,如有错误望大家指出

 

#include <iostream>
#include <cstdio>
#include <cstring>
#include <cstdlib>


using namespace std;

#define MAXN 100
#define INF 1000000

class Mat_Graph
{
public:
	Mat_Graph(int num):n(num){
		memset(Map,0,sizeof(Map));
		int i,j;
		for(i=1; i<=n; i++)
		{
			for(j=1; j<=n; j++)
			{
				if(i!=j)
					Map[i][j] = INF;
			}
		}
	}
	Mat_Graph(Mat_Graph *W)
	{
		int i,j;

		n = W->n;
		for(i=1; i<=n; i++)
			for(j=1; j<=n; j++)
			{
				Map[i][j] = W->Map[i][j];
			}
	}

	void AddSingleEdge(int start, int end, int weight=1)
	{
		Map[start][end] = weight;
	}
	void AddDoubleEdge(int a, int b, int weight=1)
	{
		AddSingleEdge(a,b,weight);
		AddSingleEdge(b,a,weight);
	}
	void DeleteSingleEdge(int start, int end)
	{
		Map[start][end] = INF;
	}
	void DeleteDoubleEdge(int a, int b)
	{
		DeleteSingleEdge(a,b);
		DeleteSingleEdge(b,a);
	}
	void Print_Edge()
	{
		int i,j;
		for(i=1; i<=n; i++)
		{	
			printf("%d->",i);
			for(j=1; j<=n; j++)
			{
				if(Map[i][j]!=0 && Map[i][j]!=INF)
					printf("->%d",j);
			}
			printf("\n");
		}
		printf("\n\n");
	}
	void Print_Matrix()
	{
		int i,j;
		for(i=1; i<=n; i++)
		{	
			for(j=1; j<=n; j++)
			{
				printf("%9d ",Map[i][j]);
			}
			printf("\n");
		}
		printf("\n\n");
	}


	int Map[MAXN+4][MAXN+4];
	int n;	//点的数量
	int m;	//边的数量
};


//附加-》矩阵的乘法
Mat_Graph* Matrix_Multiply(Mat_Graph *A, Mat_Graph *B)
{
	int n = A->n;
	int i,j,k;

	Mat_Graph *C = new Mat_Graph(n);
	for(i=1; i<=n; i++)
		for(j=1; j<=n; j++)
		{
			C->Map[i][j] = 0;
			for(k=1; k<=n; k++)
			{
				C->Map[i][j] = C->Map[i][j]+ A->Map[i][k]*B->Map[k][j];
			}
		}
	
	return C;
}


//工具函数
int min(int a, int b)
{
	return b>a ? a:b;
}

Mat_Graph* Extend_Shortest_Paths(Mat_Graph *L, Mat_Graph *W)
{
	int i,j,k;
	int n = L->n;
	Mat_Graph *ret = new Mat_Graph(n);
	
	for(i=1; i<=n; i++)
	{
		for(j=1; j<=n; j++)
		{
			if(i!=j)
				ret->Map[i][j] = INF;
			for(k=1; k<=n; k++)
			{
				if(L->Map[i][k]!=INF && W->Map[k][j]!=INF)  
					ret->Map[i][j] = min(ret->Map[i][j], L->Map[i][k]+W->Map[k][j]);
			}
		}
	}

	return ret;
}

Mat_Graph* Slow_Pairs_Shortest_Paths(Mat_Graph *W)
{
	int n = W->n;
	int m;

	Mat_Graph *L = new Mat_Graph(W);
	for(m=2; m<=n-1; m++)
	{
		L = Extend_Shortest_Paths(L,W);
		L->Print_Matrix();
	}

	return L;
}


Mat_Graph* Faster_All_Pairs_Shortest_Paths(Mat_Graph *W)
{
	int m;
	int n = W->n;

	Mat_Graph *L = new Mat_Graph(W);
	m = 1;

	while(m<n-1)
	{
		L = Extend_Shortest_Paths(L,L);
		m = 2*m;
		L->Print_Matrix();
	}

	return L;
}

#define UNSUBMIT
int main()
{
#ifdef UNSUBMIT
	freopen("data.in","r",stdin);
#endif
	int n,m;
	int start,end,weight;

	cin>>n>>m;			//输入要创建的图的点数和边数
	Mat_Graph *G = new Mat_Graph(n);
	while(m)
	{
		cin>>start>>end>>weight;
		G->AddSingleEdge(start, end, weight);
		m--;
	}
	G->Print_Edge();
	Mat_Graph *result = Slow_Pairs_Shortest_Paths(G);
	result->Print_Matrix();

	printf("\n\n\n");
	result = Faster_All_Pairs_Shortest_Paths(G);
	result->Print_Matrix();


	return 0;
}


//数据-》图25.2
/*
6 10
1 5 -1
2 1 1
2 4 2
3 2 2
3 6 -8
4 1 -4
4 5 3
5 2 7
6 2 5
6 3 10
*/


 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值