链接
http://codevs.cn/problem/1358/
题解
f[i][j][k]表示走到(i,j)这个格子状态为k的最小路径长度(对应位置上是1或0分别代表这个数字选过或位选过)
f[N][N][1023]就是答案。
代码
//状压dp
#include <cstdio>
#include <algorithm>
#include <cstring>
#define maxn 11
#define inf 0x3f3f3f3f
using namespace std;
int f[maxn][maxn][1024], num[maxn][maxn], N;
inline void input()
{
int i, j;
N=10;
for(i=1;i<=N;i++)for(j=1;j<=N;j++)scanf("%d",num[i]+j);
}
inline void update(int x1, int y1, int x2, int y2, int k)
{
int &f1=f[x1][y1][k], &f2=f[x2][y2][k|(1<<num[x2][y2])];
if(f1+num[x2][y2]<f2)f2=f1+num[x2][y2];
}
inline void dp()
{
int i, j, k;
memset(f,inf,sizeof(f));
f[1][1][1<<num[1][1]]=num[1][1];
for(i=1;i<=N;i++)for(j=1;j<=N;j++)for(k=0;k^1024;k++)
{
if(f[i][j][k]==inf)continue;
if(i^N)update(i,j,i+1,j,k);
if(j^N)update(i,j,i,j+1,k);
}
printf("%d",f[N][N][1023]);
}
int main()
{
input();
dp();
return 0;
}