小A点菜

小A点菜

方案数问题.背包.

 

 

 使用dp[i][j]表示前i道菜刚好能花费完j钱的方案数,压成一维.(dp[j])

那么明显地,dp[0]=1.

对于每个j,花完j钱的方案划分为两种:点了i菜和没点i菜,将这两种情况的方案数加起来,即dp[j] = dp[j] + dp[j - w[i]].(加号左边表示没点i菜,不好理解就还原成二维再想想)

即dp[j] += dp[j - w[i]].

本质上是对于每种菜选还是不选做出判断和统计.

背包问题即选与不选的问题.

再往前推一些,最初学到的解决这种问题的方法是搜索,回溯,这种动态规划与之思想十分相近.

这时候需要看知乎,总会有启发.

搜索和动态规划的联系究竟在哪里?

#include <algorithm>
#include <cstdio>
#include <cstring>
#include <iostream>
using namespace std;

int n, m, w[110], dp[10010];

int main(){
    cin >> n >> m;
    for(int i = 0; i < n; i++) cin >> w[i];

    for(int i = 0; i < n; i++)
        for(int j = m; j >= w[i]; j--){
            dp[0] = 1;
            dp[j] += dp[j - w[i]];
        }

    cout << dp[m] << endl;

    return 0;
}
View Code
posted @ 2020-12-04 15:22  goverclock  阅读(50)  评论(0编辑  收藏  举报