记一次坑die(误)的题目--HDU2553--(DFS)
,N皇后问题
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) |
Total Submission(s): 720 Accepted Submission(s): 417 |
|
Problem Description
在N*N的方格棋盘放置了N个皇后,使得它们不相互攻击(即任意2个皇后不允许处在同一排,同一列,也不允许处在与棋盘边框成45角的斜线上。
你的任务是,对于给定的N,求出有多少种合法的放置方法。 |
Input
共有若干行,每行一个正整数N≤10,表示棋盘和皇后的数量;如果N=0,表示结束。
|
Output
共有若干行,每行一个正整数,表示对应输入行的皇后的不同放置数量。 |
Sample Input
1 8 5 0 |
Sample Output
1 92 10 |
Author
cgf
|
Source
2008 HZNU Programming Contest
|
Recommend
lcy
|
一道搜索的经典题目, 特别水, 但坑了我半天.
交了三遍一直超时, 但这道题实在想不出有好的优化方法....只得祭出终极神器----"打表"....(汗)
46ms过, 汗.....坑die(误)...
这得有多少重复的测试数据啊....
代码
1 #include<iostream> 2 #include<cstdio> 3 #include<cstring> 4 #include<algorithm> 5 #include<cmath> 6 #include<map> 7 #include<iomanip> 8 #include<queue> 9 #define INF 0x7ffffff 10 #define MAXN 15 11 using namespace std; 12 const double eps=1e-10; 13 int res; 14 int m[MAXN][MAXN]; 15 int n; 16 int xx,yy; 17 int num[MAXN]; 18 bool ok(int x,int y) 19 { 20 for(int i=1;i<=n;i++){ 21 if(m[x][i]&&i!=y) 22 return 0; 23 } 24 xx=x;yy=y; 25 while(xx<n&&yy<n){ 26 xx+=1; yy+=1; 27 if(m[xx][yy]) 28 return 0; 29 } 30 xx=x;yy=y; 31 while(xx>1&&yy>1){ 32 xx-=1;yy-=1; 33 if(m[xx][yy]) 34 return 0; 35 } 36 xx=x;yy=y; 37 while(xx<n&&yy>1){ 38 xx++; yy--; 39 if(m[xx][yy]) 40 return 0; 41 } 42 while(x>1&&y<n){ 43 x--;y++; 44 if(m[x][y]) 45 return 0; 46 } 47 return 1; 48 } 49 void dfs(int x,int y) 50 { 51 if(ok(x,y)){ 52 if(y==n){ 53 res++; 54 return; 55 } 56 for(int i=1;i<=n;i++){ 57 m[i][y+1]=1; 58 dfs(i,y+1); 59 m[i][y+1]=0; 60 } 61 } 62 else return; 63 } 64 void set() 65 { 66 for(int i=1;i<=10;i++){ 67 n=i; 68 res=0; 69 dfs(0,0); 70 num[i]=res; 71 } 72 } 73 int main() 74 { 75 #ifndef ONLINE_JUDGE 76 freopen("data.in", "r", stdin); 77 #endif 78 std::ios::sync_with_stdio(false); 79 std::cin.tie(0); 80 set(); 81 while(cin>>n&&n!=0){ 82 // memset(m,0,sizeof(m)); 83 // res=0; 84 // dfs(0,0); 85 cout<<num[n]<<endl; 86 } 87 }