HDU 5464 ( Clarke and problem ) (dp)

dp[i][j] := 前i个数和为j的情况(mod p)

dp[i][j] 分两种情况 1.不选取第i个数 -> dp[i][j] = dp[i-1][j]

                          2.   选取第i个数 -> dp[i][j] = dp[i-1][t] ((t+a[i])%p==j)

(为什么很简单的题,思路也有了,比赛的时候就是写不对呢?)

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

typedef long long ll;

ll a[1005];
ll dp[1005][1005];
const ll MOD = 1000000007;

int main()
{
    int t, n, p;
    scanf("%d", &t);
    while (t--) {
        memset(dp, 0, sizeof dp);
        scanf("%d%d", &n, &p);

        for (int i = 1; i <= n; ++i) {
            scanf("%I64d", &a[i]);
        }
		dp[0][0] = 1;
        for (int i = 1; i <= n; ++i) {
            for (int j = 0; j < p; ++j) {
                int temp = (j - (a[i] % p) + p) % p;
                dp[i][j] = (dp[i - 1][temp] + dp[i - 1][j]) % MOD;
            }
        }
        printf("%I64d\n", dp[n][0]);
    }
    return 0;
}

/**
Input:
78
4 2
1 2 3 4

Output:
8
*/

  

posted @ 2015-09-22 20:14  我不吃饼干呀  阅读(137)  评论(0编辑  收藏  举报