动态规划-3.1.2矩阵连乘问题之迭代法(自底向上)

问题描述:给定n个矩阵{A1,A2,…,An},其中Ai与Ai+1是可乘的,i=1,2…,n-1。如何确定计算矩阵连乘积的计算次序,使得依此次序计算矩阵连乘积需要的数乘次数最少
问题分析:由于矩阵乘法满足结合律,所以计算矩阵的连乘可以有许多不同的计算次序。这种计算次序可以用加括号的方式来确定。
若一个矩阵连乘积的计算次序完全确定,也就是说该连乘积已完全加括号,则可以依此次序反复调用2个矩阵相乘的标准算法计算出矩阵连乘积

基于矩阵连乘的动态规划思想步骤

(1)找出最优解的性质,刻画其特征结构
(2)建立递归关系
设计算A[i:j],1≤i≤j≤n,所需要的最少数乘次数m[i,j],则原问题的最优值为m[1,n] 。
这里,A[i]的维数为p[i-1]*p[i]。

①当i=j时,A[i,j]=Ai, m[i,j]=0;(表示只有一个矩阵,如A1,没有和其他矩阵相乘,故乘的次数为0)
②当i< j时,m[i,j]=min{m[i,k]+m[k+1,j] +pi-1*pk*pj} ,其中 i <= k< j
1
(3)计算最优值
(4)构造最优解

基于矩阵连乘的算法实现步骤

1. 先初始化m[i][i]
2. 依次从链长为[2:n]递增分别计算不同链长的矩阵连乘最优值
3.1 先令m[i][j]最优值为矩阵链首元素划分下的值,后再进行对比
3.2 计算k∈[i+1:j-1]递增划分下最优值,并和之前已保存的最优值对比,取小者

如题所示:
2
分析结果如下:
3
举例说明:
4
程序代码如下:

public class test3_1_2 {
    public static void matrixChain(int[] p,int[][] m,int[][] s){
        int n = p.length-1;
        //1.先初始化m[i][i]
        for(int i=1;i<=n;i++) m[i][i] = 0;
        //2.依次从链长为[2:n]递增分别计算不同链长的矩阵连乘最优值
        for(int r=2;r<=n;r++)  
            for(int i=1;i<=n-(r-1);i++){   //当计算链长为r时,i的取值范围
                int j = i+r-1; //每条矩阵链m[i][j]  i表示矩阵链首元素下标;j表示矩阵链的尾元素下标
                //3.1先令m[i][j]最优值为矩阵链首元素划分下的值,后再进行对比
                m[i][j] = m[i+1][j]+p[i-1]*p[i]*p[j]; 
                //完整表达式为m[i][j]=m[i][i]+m[i+1][j]+p[i-1]*p[i]*p[j];因m[i][i]=0故省去,此时的"k"=i
                s[i][j] = i;
                //3.2计算k∈[i+1:j-1]递增划分下最优值,并和之前已保存的最优值对比,取小者
                for(int k=i+1;k<j;k++){
                    int t = m[i][k]+m[k+1][j]+p[i-1]*p[k]*p[j];
                    if(t<m[i][j]){
                        m[i][j] = t;
                        s[i][j] = k;
                    }
                }
            }
    }
    public static void traceback(int[][] s,int i,int j){
        if(i==j) return;
        traceback(s,i,s[i][j]);
        traceback(s,s[i][j]+1,j);
        System.out.println("(A"+i+"。。。"+"A"+s[i][j]+")(A"+(s[i][j]+1)+"。。。"+"A"+j+")");
    }
    public static void main(String[] args) {
        int[] p = {30,35,15,5,10,20,25};
        int n = p.length;
        int[][] m = new int[n][n];
        int[][] s = new int[n][n];  
        matrixChain(p,m,s);
        System.out.println("矩阵连乘最优值为:"+m[1][n-1]);
        traceback(s,1,n-1);
    }
}

运行结果:

矩阵连乘最优值为:15125
(A2。。。A2)(A3。。。A3)
(A1。。。A1)(A2。。。A3)
(A4。。。A4)(A5。。。A5)
(A4。。。A5)(A6。。。A6)
(A1。。。A3)(A4。。。A6)

总结:算法matrixChain的主要计算量取决于算法中对r,i和k的3重循环。循环体内的计算量为O(1),而3重循环的总次数为O(n^3)。因此算法的计算时间上界为O(n^3)。算法所占用的空间显然为O(n2)。

动态规划法:当解某一问题的直接递归算法所产生的递归树中,相同的子问题反复出现,并且不同子问题的个数又相对较少时,用动态规划算法是有效的。

  • 4
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 4
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

SL_World

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值