矩阵连乘

矩阵连乘

知识标签:DP,algorithm


推导公式

d[i][j]={0minik<j{d[i,k]+d[k+1,j]+pi1pkpj},i=j,i<j d [ i ] [ j ] = { 0 ,如果i=j min i ≤ k < j { d [ i , k ] + d [ k + 1 , j ] + p i − 1 p k p j } ,如果i<j

d[i][j] d [ i ] [ j ] :从矩阵i到矩阵j连乘所需乘法次数最少值
pk p k :对于第k个矩阵 20×10 20 × 10 pk p k 表示 10 10 pk1 p k − 1 表示 20 20

  • 分析此公式可知当 i>j i > j 时无意义,即全部 d[i][j] d [ i ] [ j ] 值构成的矩阵为三角矩阵
  • d[ij] d [ i , j ] 开始,其中 i=1,j=i+1 i = 1 , j = i + 1 ,即先求 (1,2),(2,3),(3,4)... ( 1 , 2 ) , ( 2 , 3 ) , ( 3 , 4 ) . . . 这个斜对角线的 d[i][j] d [ i ] [ j ]
  • 然后向下循环, i=1,j=i+2 i = 1 , j = i + 2 ,即求 (1,3),(2,4)(3,5)... ( 1 , 3 ) , ( 2 , 4 ) ( 3 , 5 ) . . . 这个斜对角线的 d[i][j] d [ i ] [ j ]
  • 然后继续下去,直到把 (1,t) ( 1 , t ) 求完,其中 t t 表示矩阵个数

code

代码中m数组中存放pk的值

#include<iostream>
#include<string.h>

#define MAX 2100000000
#define SIZE 100

int d[SIZE][SIZE];
int m[SIZE];

int matrix_DP(int n)
{
    int sum;
    memset(d, 0, sizeof(d));
    //每循环一次计算一条斜对角线
    for(int len = 2; len < n; ++len)
    {//第一次循环计算斜对角线(1,2),(2,3),(3,4)...

        for(int i = 1, j = len; j < n; ++i, ++j)
        {
            int min = MAX;
            //k在[i,j)范围内
            for(int k = i; k != j; ++k)
            {
                sum = d[i][k] + d[k + 1][j] + m[i - 1] * m[k] * m[j];
                if(sum < min)
                {
                    min = sum;
                }
            }
            d[i][j] = min;
        }
    }
    //返回从第一个矩阵到最后一个矩阵的最少乘法次数
    return d[1][n - 1];
}

int main(void)
{
    int len = -1;
    while(std::cin >> m[++len]);
    //len为数组m的长度
    std::cout << "len : "<< len << std::endl;
    std::cout << "matrix_DP return :" << matrix_DP(len) << std::endl;

    //输出d[i][j]
    for(int i = 1; i < len; ++i)
    {
        std::cout << std::endl;
        for(int j = 1; j < len; ++j)
        {
            std::cout << d[i][j] << '\t' << std::flush;
        }
        std::cout << std::endl;
    }
    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值