http://acm.hdu.edu.cn/showproblem.php?pid=1045

在最多为 4 * 4 的方阵中,圆形代表堡垒,正方形代表墙,堡垒射出的子弹无法穿过墙,求任何两个堡垒都不能射中对方的最大的堡垒放置数?
#pragma warning (disable:4786)
#include<iostream>
#include<string>
#include<algorithm>
using namespace std;
string map[6];
int arr[20]; //总元素数组
int used_row[6],used_column[6]; //标记行和列是否已被使用
int n; //行(列)数
int DFS( int index ){
if( index == n * n )
return 0;
//根据元素的坐标计算其所在行列数
int row = index / n;
int column = index % n;
//如果是墙,将其所在的行和列设置为未使用
if( arr[ index ] == 1 ){
used_row[row] = 0;
used_column[column] = 0;
return DFS( index + 1 );
}
//对两种情况进行回溯,一种是在该处放置堡垒,另一种是不放置
int re1 = DFS( index + 1 );
int re2 = 0;
if( used_row[row] == 0 && used_column[column] == 0 ){
used_row[row] = 1;
used_column[column] = 1;
re2 = DFS( index +1 ) + 1;
//不要忘了恢复状态
used_row[row] = 0;
used_column[column] = 0;
}
//返回放置和不放置堡垒两种情况中得到较好结果的那种
if( re2 < re1 )
return re1;
else return re2;
}
int main(){
int i,j;
while( scanf( "%d", &n ) && n ){
memset( used_row, 0, sizeof( used_row ) );
memset( used_column, 0, sizeof( used_column ) );
memset( arr, 0, sizeof(arr) );
string s;
for( i = 0; i < n; i ++ ){
cin>>map[i];
for( j = 0; j < n; j ++ ){
if( map[i][j] == 'X' )
arr[i * n + j] = 1;
}
}
printf( "%d\n", DFS( 0 ) );
}
}

本文探讨了在最多为4*4的方阵中,如何通过回溯算法找到任何两个堡垒都不能射中对方的最大堡垒放置数。
2027

被折叠的 条评论
为什么被折叠?



