题解 | #小红取数#

小红取数

http://www.nowcoder.com/practice/6a7b2b6c9e3a4f56b1db9f8ca08d889b

思路解析: 如何想到动态规划的递推式是最重要的。

1.如果我们采取一维的数组,那么没法同时满足两个条件。所以采取二维数组进行数据的存储。

2.利用dp[i][j],将第一个i表示前i个数值,j表示前i个数值modk后的余数值。而dp[i][j]整体表示前i个数值在余j时的最大值,而我们需要获得的是dp[n][0],即前n个数值,余0时的最大值。

3.dp[i - 1][j] + num[i]表示在前i-1个数的基础上,加入第i个数值时的最大值,那么此时的余数为(j + num[i]) % k,即dp[i][(j + num[i]) % k] = dp[i - 1][j] + num[i]。当然,这是将第i个数值加入时的最大值,若不加入时,是否存在更大的值,即dp[i][(j + num[i]) % k] = dp[i - 1][(j + num[i]) % k]。


#include<iostream>
using namespace std;
long long int num[1001],dp[1010][1010];
int main()
{
    ios::sync_with_stdio(false);
    cin.tie(0);
    int n,k;
    cin >> n >> k;
    for(int i = 0;i < n;++i)
        cin >> num[i];
    for(int i = 0;i <= n;++i)
        for(int j = 0;j < k;++j)
            dp[i][j] = -1e18;
    dp[0][0] = 0;
    for(int i = 1;i <= n;++i)
        for(int j = 0;j < k;++j)
            dp[i][(j + num[i - 1]) % k] = max(dp[i - 1][j] + num[i - 1],dp[i - 1][(j + num[i - 1]) % k]);
    if(dp[n][0] <= 0)
        cout << -1;
    else
        cout << dp[n][0];
}
全部评论

相关推荐

10-11 17:45
门头沟学院 Java
走吗:别怕 我以前也是这么认为 虽然一面就挂 但是颇有收获!
点赞 评论 收藏
分享
10-21 23:48
蚌埠坦克学院
csgq:可能没hc了 昨天一面完秒挂
点赞 评论 收藏
分享
点赞 收藏 评论
分享
牛客网
牛客企业服务