【发布时间】:2016-11-08 00:08:28
【问题描述】:
这是我接受的 Codeforces 问题代码:Education Round 1E
根据经验,我可以自信地解决它,但我总是发现我很难分析这种算法的时间复杂度(通常是 DP 中的递归)
#include<bits/stdc++.h>
using namespace std;
int t;
int N,M,K;
int dp[32][32][52];
int DP(int n, int m, int k){
if(k > n*m) return 1<<28;
if(k == n*m || k <= 0) return 0;
if(dp[n][m][k] != 1<<28) return dp[n][m][k];
for(int i=1; i<n; i++)
for(int j=0; j<=k; j++)
dp[n][m][k] = min(dp[n][m][k], DP(i, m, j) + DP(n-i, m, k-j) + m*m);
for(int i=1; i<m;i++)
for(int j=0; j<=k; j++)
dp[n][m][k] = min(dp[n][m][k], DP(n, i, j) + DP(n, m-i, k-j) + n*n);
return dp[n][m][k];
}
int main() {
cin >> t;
for(int i=0; i<32;i++) for(int j=0; j<32;j++) for(int k=0; k<52;k++) dp[i][j][k] = 1 << 28;
while(t--){
cin >> N >> M >> K;
cout << DP(N,M,K) << endl;
}
return 0;
}
分析DP(N,M,K)之类的函数复杂度的常见做法是什么?我不认为主定理可以在这里应用,因为每个子问题的大小都不相同(但我不确定)。
【问题讨论】:
标签: recursion time-complexity c++14 dynamic-programming code-analysis