算法分析第八次作业
1. 问题
给定n个矩阵{A1,A2,…,An},其中Ai与Ai+1是可乘的,i=1,2 ,…,n-1。如何确定计算矩阵连乘积的计算次序,使得依此次序计算矩阵连乘积需要的数乘次数最少。
2. 解析
这其实是个很简单的问题,区间dp模板题,dp[i][j],表示区间i到j合并的最小值,枚举k表示分割点,dp[1][n]即为答案
转移方程:dp[i][j]=min(dp[i][j],dp[i][k]+d[k+1][j]+b[i]*b[k+1]*b[j+1]
3. 设计
1 2 3 4 5 6 7 8 9 | for ( int h = 1; h < n; h++) { //区间dp for ( int i = 1; i <= n - h; i++) { int j = i + h; for ( int k = i; k <= j - 1; k++) { if (dp[i][j]==0) dp[i][j]=dp[i][k] + dp[k + 1][j] + b[i] * b[k + 1] * b[j + 1]; else dp[i][j]=min(dp[i][j],dp[i][k] + dp[k + 1][j] + b[i] * b[k + 1] * b[j + 1]); } } } |
4. 分析
复杂度 O(n3)
5. 源码
https://github.com/Tinkerllt/algorithm-work.git
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 | #include<stdio.h> #include<iostream> #include<cmath> #include<cstring> #include<algorithm> #include<bitset> #include<set> #include<deque> #include<queue> #include<vector> //#include<unordered_map> #include<map> #include<stack> using namespace std; #define ll long long #define ull unsigned long long #define pii pair<int,int> #define Pii pair<ll,int> #define m_p make_pair #define l_b lower_bound #define u_b upper_bound const int inf = 0x3f3f3f3f; const ll linf = 0x3f3f3f3f3f3f3f3f; const int maxn = 600 + 11; const int maxm = 600 + 11; const int mod = 1e9 + 7; const double eps = 1e-5; ll rd() { ll x = 0, f = 1; char ch = getchar (); while (ch< '0' || ch> '9' ) { if (ch == '-' )f = -1; ch = getchar (); } while (ch >= '0' &&ch <= '9' ) { x = x * 10 + ch - '0' ; ch = getchar (); } return x * f; } inline ll qpow(ll a, ll b, ll p) { ll res = 1; while (b) { if (b & 1) { res *= a; res %= p; }b >>= 1; a = a * a%p; } return res; } inline ll gcd(ll a, ll b) { if (b == 0) return a; return gcd(b, a%b); } //iterator //head //priority_queue int b[maxn], dp[maxn][maxn],a[maxn]; int main() { int n; memset (dp, 0, sizeof dp); cin >> n; cin >> b[1] >> b[2]; for ( int i = 3; i <= n + 1; i++) { cin >> a[i] >> b[i]; } for ( int h = 1; h < n; h++) { //区间dp for ( int i = 1; i <= n - h; i++) { int j = i + h; for ( int k = i; k <= j - 1; k++) { if (dp[i][j]==0) dp[i][j]=dp[i][k] + dp[k + 1][j] + b[i] * b[k + 1] * b[j + 1]; else dp[i][j]=min(dp[i][j],dp[i][k] + dp[k + 1][j] + b[i] * b[k + 1] * b[j + 1]); } } } cout << dp[1][n] << endl; return 0; } |
【推荐】还在用 ECharts 开发大屏?试试这款永久免费的开源 BI 工具!
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步