算法提高 矩阵乘法

这道题当初做的时候完全没思路,对DP也是完全搞不懂。现在抽时间复习了一下,看着DP函数部分还是一脸懵逼,上网找了找答案,可是要么讲的很复杂,要么直接给代码,给我造成了特别大的困扰。所以自己把测试用例带入,跟着编译器走了一遍,豁然开朗,原来是这么回事
下面是测试部分:
0 2 1  dp[1[2]=50
1 3 2  dp[2][3]=1000
0 3 1  dp[1][3]=1200 
0 3 2  dp[1][3]=150
看见这个瞬间就明白了,适用二维的dp[i][j]数组i代表起始位置a0,j代表末位置an知道dp数组的含义,动规就简单了。当初迷迷糊糊的不知道dp的意思,导致对这个题根本就理解的不了。分析测试部分的两个dp[1][3]应该就可以知道k在段代码中的作用的。
注意:代码中的数据类型需要自己改一下,这里是重新写了这个题目,重新理解一下动规,所以对数据类型就只用了int。题目中所要求的数据比较大。所以数据类型的选择很重要。代码中定义的宏变量INF需要15个9才能通过所有测试用例(因为这个错误,当初提交代码提交了好几次)。
动规中,如果是和max函数相关,dp初始化为一个0就可以,如果是min函数,特别小心dp初始化的值,尽量设置大一点(当然不能让编译器报错)这对蓝桥这种坑题有好处。
学习中不能理解的代码,耐着性子,调试几遍,会有意想不到的收获的。

才知道自己能力有多弱了,知识空白点太多了还要不断的学习学习啊。推荐这个博客http://blog.csdn.net/f_zyj?viewmode=contents她对题目的讲解特别详细。一看就会。
#include<stdio.h>
#define INF 9999999999
int dp[1005][1005];//i代表起始点,j代表末尾点 
int num[10005];//矩阵元素
int min(int a,int b){
	return a>b?b:a;
} 
int DP(int n){
	int i,j,k;
	for(j=2;j<=n;j++){
		for(i=j-1;i>0;i--){
			dp[i][i]=dp[j][j]=0;//自己到自己的运算次数为零 
			for(k=i;k<j;k++){
				dp[i][j]=min(dp[i][j],dp[i][k]+dp[k+1][j]+num[i-1]*num[k]*num[j]);
			}
		}
	}
	return dp[1][n];//返回起始点和终点的dp 
	
}
int main(void){
	int n;//矩阵个数
	int i,j;
	int temp;
	scanf("%d",&n);
	for(i=0;i<=n;i++){
		scanf("%d",&num[i]);//矩阵元素的输入 
	}
	if(n==1){
		printf("%d\n",num[0]*num[1]);
		return 0;
	}
	for(i=0;i<=n;i++){
		for(j=0;j<=n;j++){
			dp[i][j]=dp[j][i]=INF;//这里是一个无限大的值,因为是求min 
		}
	}
	temp=DP(n);
	printf("%d\n",temp);
	return 0;
}


评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值