51nod oj 1140 矩阵相乘结果的判断【矩阵的结合律】

本文介绍了一种通过利用矩阵乘法的结合律特性进行优化的方法,从而将原本的时间复杂度从O(N^3)降低到O(N^2),并通过构造特定矩阵进行验证。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >


题目链接:1140


题目来源:  POJ
基准时间限制:1 秒 空间限制:131072 KB 分值: 80  难度:5级算法题
 收藏
 关注
给出三个N*N的矩阵A, B, C,问A * B是否等于C?
Input
第1行,1个数N。(0 <= N <= 500)
第2 - N + 1行:每行N个数,对应矩阵A的元素。(0 <= M[i] <= 16)
第N + 2 - 2N + 1行:每行N个数,对应矩阵B的元素。(0 <= M[i] <= 16)
第2N + 2 - 3N + 1行:每行N个数,对应矩阵C的元素。
Output
如果相等输出Yes,否则输出No。
Input示例
2
1 0
0 1
0 1
1 0
0 1
1 0
Output示例
Yes


矩阵的乘法---为O(N^3)-----500^3=1.25*10^8--------超时

所以需要优化---通过矩阵的结合律可以将时间复杂度降到O(N^2)

构造一个行矩阵或者列矩阵X----1*n------

A*B==C           可以推出           X*A*B=X*C

而X*A的复杂度为1*N*N--------

为了保证程序的测定更准确---我们通过随机数来构造X----也可多构造几组X----


代码:

#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
long long a1[2][520],a2[2][520],a3[2][520],a,kp[2][520];
int main()
{
	int n;scanf("%d",&n);
	for (int i=1;i<=n;i++)
	{
		kp[0][i]=rand()%10000+2;
		kp[1][i]=rand()%10000+2; 
	}
	memset(a1,0,sizeof(a1));
	memset(a2,0,sizeof(a2));
	memset(a3,0,sizeof(a3));
	for (int i=1;i<=n;i++)
	{
		for (int j=1;j<=n;j++)
		{
			scanf("%lld",&a);
			a1[0][j]+=kp[0][i]*a;
			a1[1][j]+=kp[1][i]*a;
		}
	}
	for (int i=1;i<=n;i++)
	{
		for (int j=1;j<=n;j++)
		{
			scanf("%lld",&a);
			a2[0][j]+=a1[0][i]*a;
			a2[1][j]+=a1[1][i]*a;
		}
	}
	for (int i=1;i<=n;i++)
	{
		for (int j=1;j<=n;j++)
		{
			scanf("%lld",&a);
			a3[0][j]+=kp[0][i]*a;
			a3[1][j]+=kp[1][i]*a;
		}
	}
	bool fafe=true;
	for (int i=1;i<=n;i++)
	if (a2[0][i]!=a3[0][i]||a2[1][i]!=a3[1][i])
	{
		fafe=false;
		break;
	}
	printf("%s\n",fafe?"Yes":"No");
	return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值