1、N皇后问题
在N*N的方格棋盘放置了N个皇后,使得它们不相互攻击(即任意2个皇后不允许处在同一排,同一列,也不允许处在与棋盘边框成45角的斜线上。
你的任务是,对于给定的N,求出有多少种合法的放置方法。
#include<stdio.h>
int hang[300][300]= {0,0};
int lie[30]= {0};
int cnt=0;
int ans[30][30];
void solve(int nowhang,int n) {
// printf("$$ %d\n",nowhang);
if(nowhang==n+1) {
cnt++;
/* int i,j;
for(i = 1; i <= n; ++i) {
for(j = 1; j <= n; ++j) {
printf("%d\t",ans[i][j]);
}
puts("");
}
puts("===");*/
return ;
}
int i,j;
for(i=1; i<=n; i++) { //lie
if(lie[i]==1||hang[nowhang][i]!=0) continue; //列有皇后,或这一个位子是上一行皇后的对角位子
else {
// printf("%d %d OK\n",nowhang,i);
lie[i]=1;
for(j=1; nowhang+j<=n; j++) //nowhang的i列可以填
hang[nowhang+j][i+j]++;//i列nowhang的下一行的左右
for(j=1; nowhang+j<=n&&i-j>0; j++)
hang[nowhang+j][i-j]++;
ans[nowhang][i] = 1;
solve(nowhang+1,n);
// printf("%d ",cnt);
lie[i]=0;
for(j=1; nowhang+j<=n; j++)
hang[nowhang+j][i+j]--;
for(j=1; nowhang+j<=n&&i-j>0; j++)
hang[nowhang+j][i-j]--;
ans[nowhang][i] = 0;
}
}
}
int main() {
// freopen("out.txt","w",stdout);
int n;
int p;
int huang[20]={0};
for(p=1;p<=10;p++)
{
cnt=0;
solve(1,p);
huang[p]=cnt;
}
while(scanf("%d",&n),n!=0) {
printf("%d\n",huang[n]);
}
}
Lake Counting
Due to recent rains, water has pooled in various places in Farmer John’s field, which is represented by a rectangle of N x M (1 <= N <= 100; 1 <= M <= 100) squares. Each square contains either water (‘W’) or dry land (‘.’). Farmer John would like to figure out how many ponds have formed in his field. A pond is a connected set of squares with water in them, where a square is considered adjacent to all eight of its neighbors.
Given a diagram of Farmer John’s field, determine how many ponds he has.
Line 1: Two space-separated integers: N and M
Lines 2..N+1: M characters per line representing one row of Farmer John’s field. Each character is either ‘W’ or ‘.’. The characters do not have spaces between them.
Sample Input
10 12
W……..WW.
.WWW…..WWW
….WW…WW.
………WW.
………W..
..W……W..
.W.W…..WW.
W.W.W…..W.
.W.W……W.
..W…….W.
Sample Output
3
#include<stdio.h>
#include<string.h>
char map[105][105];
int direction[8][2]={{0,1},{0,-1},{1,0},{-1,0},{1,1},{1,-1},{-1,1},{-1,-1}};
void dfs(int x,int y)
{
map[x][y]='.';
int i;
for(i=0;i<8;i++)
{
if(map[x+direction[i][0]][y+direction[i][1]]=='W')
dfs(x+direction[i][0],y+direction[i][1]);
}
}
int main()
{
int hang,lie;
scanf("%d %d",&hang,&lie);
int i,j,cnt=0;
for(i=0;i<hang;i++)
{
scanf("%s",&map[i]);
}
for(i=0;i<hang;i++)
{
for(j=0;j<lie;j++)
{
if(map[i][j]=='W')
{
cnt++;
dfs(i,j);
}
}
}
printf("%d\n",cnt);
return 0;
}
相同标记的搜索
codeforces685A
给你n和m,找出(a,b)有多少对,其中a满足要求:0<=a < n,a的7进制的位数和n-1的7进制的位数相同,b满足要求:0<=b< m,b的7进制的位数和m-1的7进制的位数相同,而且a,b中没有数字是相同的。
直接对ADFS,找到符合条件的A之后对B进行DFS找。。两个DFS公用一个visit,就可以保证A,B中没有相同的数字。
Examples Input
2 3
Output
4
Input
8 2
Output
5
Note
In the first sample, possible pairs are: (0: 1), (0: 2), (1: 0), (1: 2).
In the second sample, possible pairs are: (02: 1), (03: 1), (04: 1), (05: 1), (06: 1).
#include<bits/stdc++.h>
using namespace std;
bool visit[11];
int getnumber(int x){
int cnt=0;
if(x==0) return cnt=1;
while(x){
cnt++;
x=x/7;
}
return cnt;
}
int numa,numb;
int ans;
int n,m;
void DFSB(int wei,int B){
if(wei>numb){
if(B<m){
// cout<<B<<endl;
ans++;
}
return;
}
for(int i=0;i<7;i++){
if(visit[i]==false){
visit[i]=true;
DFSB(wei+1,B*7+i);
visit[i]=false;
}
}
}
void DFSA(int wei,int A){
if(wei>numa){
if(A<n){
// cout<<A<<"+++++++"<<endl;
DFSB(1,0);
return;
}
else return;
}
for(int i=0;i<7;i++){
if(visit[i]==false){
visit[i]=true;
DFSA(wei+1,A*7+i);
visit[i]=false;
}
}
}
int main(){
while(scanf("%d %d",&n,&m)!=EOF){
numa=getnumber(n-1),numb=getnumber(m-1);
memset(visit,false,sizeof(visit));
ans=0;
DFSA(1,0);
printf("%d\n",ans);
}
return 0;
}