POJ-1321(类8皇后问题)

来源:互联网 发布:聊天软件开发 编辑:程序博客网 时间:2024/06/06 10:03

题目:http://poj.org/problem?id=1321

分析:题目数据量很小暴搜即可


#include <cstdio>int n, k, tot;char board[10][10];void dfs(int x, int r, int u){if(!x){++tot;return;}if(r >= n) return;//try to place x on this rowfor(int c = 0; c < n; ++c){if(board[r][c] == '#' && (u & (1 << c)) == 0){dfs(x - 1, r + 1, u | (1 << c));}}//try to skip this rowif(x + r <= n) dfs(x, r + 1, u);}int main(){#ifndef ONLINE_JUDGEfreopen("__in.txt", "r", stdin);freopen("__out.txt", "w", stdout);#endifwhile(scanf("%d%d", &n, &k), n != -1){while(getchar() != '\n') ;for(int i = 0; i < n; ++i) gets(board[i]);tot = 0;dfs(k, 0, 0);printf("%d\n", tot);}return 0;}
再看暴搜的dfs函数,很容易可以想到可行的状态总共也就k*n*2^n<=8*8*2^8=2^14,也很容易将上面的暴搜修改成记忆化DP的形式


#include <cstdio>#include <cstring>int n, k, f[8][8][1<<8];char board[10][10];int dp(int x, int r, int u){if(x >= k) return 1;if(n - r < k - x) return 0;if(f[x][r][u] == -1){f[x][r][u] = 0;//try to place x on this rowfor(int c = 0; c < n; ++c){if(board[r][c] == '#' && (u & (1 << c)) == 0){f[x][r][u] += dp(x + 1, r + 1, u | (1 << c));}}//try to skip this rowf[x][r][u] += dp(x, r + 1, u);}return f[x][r][u];}int main(){#ifndef ONLINE_JUDGEfreopen("__in.txt", "r", stdin);freopen("__out.txt", "w", stdout);#endifwhile(scanf("%d%d", &n, &k), n != -1){while(getchar() != '\n') ;for(int i = 0; i < n; ++i){gets(board[i]);for(int j = 0; j < k; ++j){memset(f[j][i], -1, (1<<n)*sizeof(int));}}printf("%d\n", dp(0, 0, 0));}return 0;}

0 0
原创粉丝点击