首先要明白基础的线代知识:两个矩阵相乘之后得到的矩阵的行为前面一个矩阵的行,列为后面一个矩阵的列
例如:一个p* q的矩阵A和一个q* r的矩阵B的乘积是一个新的p*r的矩阵C
具体算法思想参考大佬精品讲解:动态规划——矩阵连乘
输入
6
30 35
35 15
15 5
5 10
10 20
20 25
输出
15125
#include <stdio.h>
#include <stdlib.h>
#define N 100
void MatrixChain(int* p, int n, long long int m[][N]) {
for (int i = 1; i <= n; i++) { //矩阵链中只有一个矩阵时,次数为0,注意m[0][X]时未使用的
m[i][i] = 0;
}
for (int r = 2; r <= n; r++) { //矩阵链长度,从长度为2开始
for (int i = 1; i <= n - r + 1; i++) { //根据链长度,控制链最大的可起始点
int j = i + r - 1; //当j - i = 1,代表链长为2
m[i][j] = m[i][i] + m[i + 1][j] + p[i - 1] * p[i] * p[j];
for (int k = i + 1; k < j; k++) { //步长>2时才会用到, 即j-i >= 2, k不止可以为1,还有多种选择
int min = m[i][k] + m[k + 1][j] + p[i - 1] * p[k] * p[j];
if (min < m[i][j]) {
m[i][j] = min; //在k的所有可能取值中,找到使得m[i][j]最小的
}//每一次给m[i][j]赋值都是逐渐在子问题上得到m[i][j]的最优解
}
}
}
printf("%lld", m[1][n]);
}
int main() {
int n, i, p[N], b;
long long int m[N][N];
scanf("%d", &n);
for (i = 0; i < n-1; ++i) scanf("%d %d", &p[i], &b);
scanf("%d %d", &p[n-1], &p[n]);//仅仅由于题目输入方式受限,才被迫这样赋值给p[0]到p[n]
MatrixChain(p, n, m);
return 0;
}