https://ac.nowcoder.com/acm/contest/57359/H
这显然要用到dp,先不管时间复杂度,考虑转移的状态与方程式,定义 f i , j , k f_{i,j,k} fi,j,k表示从 i i i点走到 j j j点在背包容量为 k k k时所能取到的最大重量,是一个简单的01背包,再定义 d p i , j dp_{i,j} dpi,j表示第 i i i次操作走到第 j j j个点所能取到的最大重量,可得转移方程式为
d p i , j = M a x k = 1 j { d p i − 1 , k + f i , j , s z i } dp_{i,j}=Max_{k=1}^{j}\{dp_{i-1,k}+f_{i,j,sz_i}\} dpi,j=Maxk=1j{dpi−1,k+fi,j,szi}
时间复杂度为 O ( n 2 m ) O(n^2m) O(n2m),题目中还有一个条件:保证对于 i > 1 i>1 i>1,有 s z i ≥ s z i − 1 sz_i\ge sz_{i-1} szi≥szi−1。显然当 m > n m>n m>ns时,对于前面的 s z sz sz,最后 n n n个 s z sz sz所能得到的结果更优,所以实质上只需计算最后 n n n个 s z sz sz即可,复杂度为 O ( n 3 ) O(n^3) O(n3)。
#include
using namespace std;
const int N=1e5+5;
long long n,m,a[205],b[205],sz[N],f[205][205][205],dp[100005][205];
int main(){
cin>>n>>m;
for(int i=1;i<=n;i++)cin>>a[i]>>b[i];
for(int i=1;i<=m;i++)cin>>sz[i];
for(int i=0;i