POJ 3311 Hie with the Pie (状压DP)

原创 2015年07月07日 19:04:29

题意:n+1个点 从0出发,遍历所有的点最后回到0,每个点可访问多次,求最小花费。

思路:因为每个点可访问多次,所以用一下floyd预处理一下图就好了,然后就是个TSP。

设dp[S][v] 为遍历状态S中的每一个节点,且最后到达S中的v的最小花费。

状态转移方程:dp[S][v] = min(dp[S][v],dp[S - {v}][u] + maps[u][v]).


我的代码:

#include<cstdio>
#include<iostream>

#define min(a,b) (a < b ? a : b)
#define max(a,b) (a > b ? a : b)

using namespace std;
typedef __int64 LL;
const LL inf = 0x3f3f3f3f;
const int maxn = 15;

LL n,maps[maxn][maxn];
LL dp[1<<maxn][maxn];

void floyd(){
    for(int k = 0;k <= n; k++){
        for(int i = 0;i <= n; i++){
            for(int j = 0;j <= n; j++){
                maps[i][j] = min(maps[i][j],maps[i][k] + maps[k][j]);
            }
        }
    }
}

void solve(){
    int Ed = 1 << n,tmp;
    for(int S = 1 ; S < Ed ; S++)
        fill(dp[S],dp[S]+n+1,inf);
    for(int S = 1 ; S < Ed ; S++){
        for(int v = 1; v <= n ; v++){
            if(S >> (v - 1) & 1){
                tmp = S & (~(1 << (v - 1)));
                if(tmp == 0){
                    dp[S][v] = maps[0][v];
                    continue;
                }
                for(int u = 1; u <= n ; u++){
                    if(tmp >> (u - 1) & 1) dp[S][v] = min(dp[S][v],dp[tmp][u] + maps[u][v]);
                }
            }
        }
    }
    LL res = inf;
    for(int v = 1; v <= n; v++){
        res = min(res,dp[Ed-1][v] + maps[v][0]);
    }
    /*for(int S = 0;S < Ed; S++){
        for(int i=1;i<=n;i++){
            cout<<dp[S][i]<<" ";
        }
        cout<<endl;
    }*/
    printf("%I64d\n",res);
}

int main(){
    while(~scanf("%I64d",&n)){
        if(n == 0) break;
        for(int i=0;i<=n;i++)
            for(int j=0;j<=n;j++)
                scanf("%I64d",&maps[i][j]);
        floyd();
        solve();
    }

    return 0;
}


版权声明:本文为博主原创文章,未经博主允许不得转载。

状态压缩dp入门 (poj3254 Corn Fields)

题目链接:http://poj.org/problem?id=3254 题意:给出一个n行m列的草地,1表示肥沃,0表示贫瘠,现在要把一些牛放在肥沃的草地上,但是要求所有牛不能相邻,问你有多...
  • y990041769
  • y990041769
  • 2014年04月28日 19:10
  • 18942

poj2411 2663 2420 dp+状态压缩(多米诺骨牌问题)

题目描述:用1*2 的矩形通过组合拼成大矩形,求拼成指定的大矩形有几种拼法。 首先 我们先求用1*2 的矩形拼成 n*m的矩形有多少种拼法 当n*m为奇数时,一定是不会拼出来的,因为想要拼出来就需...
  • shiwei408
  • shiwei408
  • 2013年04月19日 00:04
  • 7257

POJ2411 状态压缩DP

POJ2411 Mondriaan's Dream 给你n*m(1矩阵,要求用1*2的多米诺骨牌去填充,问有多少种填充方法。 分析: 首先我们定义如下这种填充表示方式:如果一个骨牌是横着放的,那么它所...
  • u013480600
  • u013480600
  • 2014年02月20日 20:17
  • 1609

POJ 3311 Hie with the Pie (状压DP)

Hie with the Pie Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 6290 ...
  • jncsw
  • jncsw
  • 2016年07月14日 15:07
  • 115

POJ 3311 Hie with the Pie 状压DP

题目描述:DescriptionThe Pizazz Pizzeria prides itself in delivering pizzas to its customers as fast as p...
  • wuxuanyi27
  • wuxuanyi27
  • 2016年03月23日 20:07
  • 130

poj 3311 Hie with the Pie(floyd + 状压dp)

Hie with the Pie Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 3541 ...
  • WEYuLi
  • WEYuLi
  • 2014年04月06日 16:12
  • 535

POJ 3311 Hie with the Pie floyd+状压DP

链接:http://poj.org/problem?id=3311 题意:有N个地点和一个出发点(N 思路:首先用floyd找到所有点之间的最短路。然后用状态压缩,dp数组一定是二维的,如...
  • u011385365
  • u011385365
  • 2014年08月25日 14:07
  • 636

poj 3311 Hie with the Pie 状压dp

//参考了挑战程序设计第二版的tsp,dp[S][v]表示在已经访问了集合S中的点情况下 //从出发访问剩下的节点并回到0号起点的最少花费dp[V][0]都是0, //从0号节点回到0花费肯定是0, ...
  • TIMELIMITE
  • TIMELIMITE
  • 2015年04月08日 20:25
  • 491

POJ3311 Hie with the Pie ACM解题报告(Floyd+状压dp)

题意是有N个城市(1~N)和一个PIZZA店(0),要求一条回路,从0出发,又回到0,而且距离最短   也就是TSP(旅行商)问题,首先不难想到用FLOYD先求出任意2点的距离dis[i][j]  ...
  • Miracle_ma
  • Miracle_ma
  • 2015年02月10日 14:29
  • 557

POJ 3311 Hie with the Pie(状压DP + Floyd)

POJ 3311 Hie with the Pie(状压DP + Floyd)
  • u012860063
  • u012860063
  • 2014年11月10日 18:59
  • 767
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:POJ 3311 Hie with the Pie (状压DP)
举报原因:
原因补充:

(最多只允许输入30个字)