HDU 5691 Sitting in Line 状压dp

Posted shuguangzw

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了HDU 5691 Sitting in Line 状压dp相关的知识,希望对你有一定的参考价值。

dp[i][j][k]代表到第i个位置,第i个位置是j,k为已经选了i个数分别是那些(2进制状压)

然后:其实真正有用的状态很少,可以写记忆化搜索,我写的BFS加速

#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <cmath>
#include <string>
#include <stack>
#include <vector>
#include <map>
#include <queue>
#include <algorithm>
#include <utility>
using namespace std;
typedef long long LL;
const int N=15;
const int INF=-15*(1e8+5);
const LL mod=1e9+7;
int dp[17][17][65537];
bool inq[17][17][65537];
int a[20],p[20],n;
int vis[20];
struct Node{
   int pos,u,cur;
   // Node(int a,int b,int c){pos=a;u=b;cur=c;}
};
queue<Node>q;
int main()
{
    int T,cas=0;
    scanf("%d",&T);
    while(T--){
       printf("Case #%d:\\n",++cas);
       memset(vis,0,sizeof(vis));
       scanf("%d",&n);
       for(int i=1;i<=n;++i){
        scanf("%d%d",&a[i],&p[i]);
        if(p[i]!=-1){
            ++p[i];
            vis[p[i]]=i;
        }
       }
       int l=(1<<n)-1;
       for(int i=0;i<=n;++i)
        for(int j=0;j<=n;++j)
         for(int k=0;k<=l;++k)
          dp[i][j][k]=INF;
        memset(inq,0,sizeof(inq));
        q.push(Node{0,0,0});dp[0][0][0]=0;
        while(!q.empty()){
           Node e=q.front();
           q.pop();
           int pos=e.pos+1;
           if(vis[pos]&&(e.cur&(1<<(vis[pos]-1)))==0){
              int aim=e.cur|(1<<(vis[pos]-1));
              if(dp[pos][vis[pos]][aim]==INF)q.push(Node{pos,vis[pos],aim});
              dp[pos][vis[pos]][aim]=max(dp[pos][vis[pos]][aim],dp[e.pos][e.u][e.cur]+a[e.u]*a[vis[pos]]);
              continue;
           }
           for(int i=1;i<=n;++i){
              if(p[i]!=-1)continue;
              if(e.cur&(1<<(i-1)))continue;
              int aim=e.cur|(1<<(i-1));
              if(dp[pos][i][aim]==INF)q.push(Node{pos,i,aim});
              dp[pos][i][aim]=max(dp[pos][i][aim],dp[e.pos][e.u][e.cur]+a[e.u]*a[i]);
           }  
        }
        int ans=INF;
        for(int i=1;i<=n;++i)
         ans=max(ans,dp[n][i][l]);
        printf("%d\\n",ans);
    }
    return 0;
}
View Code

 

以上是关于HDU 5691 Sitting in Line 状压dp的主要内容,如果未能解决你的问题,请参考以下文章

HDU 5691 Sitting in Line

hdu 5691 Sitting in Line(状压dp)

hdu 5691 Sitting in Line (状压dp)

HDU5691 Sitting in Line状压DP

hdu 5691 Sitting in Line 状压dp

HDU 5691 Sitting in Line 状压dp