HDU 5691 Sitting in Line

状态压缩DP。

dp[i][j]表示前cnt个位置放了i状态的那些数字,cnt位置放的是j这个数字的最大价值。其中cnt为i二进制中1的个数。

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

long long INF = 99999999999999999;
long long dp[70000][20];
int n;
long long a[20];
int p[20],f[20], g[20];

int main()
{
    int T; int Case = 1;
    scanf("%d", &T);
    while (T--)
    {
        scanf("%d", &n);
        memset(f, 0, sizeof f); memset(g, 0, sizeof g);
        for (int i = 1; i <= n; i++)
        {
            scanf("%lld%d", &a[i], &p[i]);
            if (p[i] == -1) continue; 
            p[i]++;
            f[p[i]] = i;
            g[i] = 1;
        }

        for (int i = 0; i<(1 << n); i++)
            for (int j = 0; j <= n; j++) dp[i][j] = -INF;

        for (int j = 1; j <= n; j++)
        {
            if (g[j] == 1 && p[j] != 1) continue;
            dp[1 << (j - 1)][j] = 0;
        }

        for (int i = 1; i<(1 << n); i++)
        {
            int cnt = 0;
            for (int j = 0; j<n; j++) if ((i&(1 << j)) !=0) cnt++;

            for (int j = 1; j <= n; j++)
            {
                if (dp[i][j] == -INF) continue;
                if (f[cnt + 1] != 0)
                {
                    dp[i | (1 << (f[cnt + 1] - 1))][f[cnt + 1]] = max(dp[i | (1 << (f[cnt + 1] - 1))][f[cnt + 1]],
                        dp[i][j] + a[f[cnt + 1]] * a[j]);
                    continue;
                }
                for (int k = 1; k <= n; k++)
                {
                    if (((1 << (k - 1))&i) != 0) continue;
                    if (g[k] == 1) continue;

                    dp[i | (1 << (k - 1))][k] = max(dp[i | (1 << (k - 1))][k],
                        dp[i][j] + a[k] * a[j]);
                }
            }
        }

        long long ans = -INF;
        for (int j = 1; j <= n; j++)
        {
            ans = max(ans, dp[(1 << n) - 1][j]);
        }
        printf("Case #%d:\n", Case++);
        printf("%lld\n", ans);
    }
    return 0;
}

 

posted @ 2016-05-23 10:48  Fighting_Heart  阅读(164)  评论(0编辑  收藏  举报