你有一个N x N棋盘,你希望在它上面放置N个国王。每一行和每列应该只包含一个国王,并且没有两个国王应该相互攻击(如果两个国王存在于共享角落的方格中,则两个国王相互攻击)。
董事会的前K行中的国王已经被放置。你被赋予这些国王的位置作为数组pos []。 pos [i]是第i行中的国王已被放置的列。所有指数均为0指数。剩下的国王可以有多少种方式摆放?
Input:
The first line contains the number of test cases T. T test cases follow. Each test case contains N and K on the first line, followed by a line having K integers, denoting the array pos[ ] as described above.
Output:
Output the number of ways to place kings in the remaining rows satisfying the above conditions. Output all numbers modulo 1000000007.
Constraints:
1 <= T <= 20
1 <= N <= 16
0 <= K <= N
0 <= pos_i < N
The kings specified in the input will be in different columns and not attack each other.
Sample Input:
5
4 1
2
3 0
5 2
1 3
4 4
1 3 0 2
6 1
2
Sample Output:
1
0
2
1
18
说明: 对于第一个例子,有一个国王已经放在第0行和第2列。第二行中的国王必须属于第0列。第三行中的国王必须属于第3列,最后一个国王必须属于第3列因此,只有一个有效的位置。
对于第二个示例,没有有效的展示位置。
我应该如何处理这个问题
答案 0 :(得分:3)
回溯可能太慢了。考虑到某一行k中的解的数量仅取决于行k-1中的王的位置和行
答案 1 :(得分:2)
你应该使用回溯来解决这个问题,如下所示的简单函数可以解决你的问题,(处理输入文件和输出很容易,所以我跳过它)。
int CanPlaceKingInPosition(int pos[],int MaxIndex,int NewCol){
for(int i=0;i<MaxIndex-1;i++)
if(pos[i]==NewCol)
return 0;
//MaxIndex is the index of the above row of the new king, so we have to check attacking conditions
if (abs(pos[MaxIndex-1]-NewCol)<=1)
return 0;
return 1;
}
int solver(int pos[], int N, int K){
int result=0;
if (K>N) //termination condition
return result;
if (K==N-1) //last row
return IsOnlyPossibleColAGoodOne(pos,N,N-1);
for (int i=0;i<N;i++){ //for each column if we can place the king in it, move one step forward
if (CanPlaceKingInPosion(pos,K,i)){
pos[K]=i; //add new king
result+=solver(pos,N,K+1);
}
}
return result;
}
你可以从main()调用这个函数,如下所示:
//read N,K
//fill pos
printf("%d",solver(pos,N,K+1) % 1000000007)
“IsOnlyPossibleColAGoodOne”函数返回1,如果可以将一个王放在船上留下的唯一空闲列中(这样做很简单)。 我没有测试过这个函数,所以你应该把它看作一个指导而不是实际代码。(它可能工作正常,但我没有测试过它)
P.S:这是一个ACM / ICPC问题吗?答案 2 :(得分:0)
Hello使用下面的代码我可以产生有效的王位置的排列,如果内存不是约束,我们可以生成高达16X16的所有排列并将它们存储在相应的表中 对于给定的测试用例生成相应的不完全排列,可以匹配已经生成的相应NXN板的排列,计算将是多么多的答案
int columns[]={1,2,3,4,5,6,7,8,9,10,11,12};
public void displayPermitationsBoth(int prev,StringBuilder sb,int n,int stage){
if(stage==n){
display(sb);
return;
}
String localStr=sb.toString();
int localStage=stage;
for(int i=0;i<n;i++){
if((sb.toString().contains("-"+Integer.toString(columns[i])+"-"))||(Math.abs(prev-columns[i])==1)){
continue;
}
displayPermitationsBoth(columns[i],sb.append("-"+columns[i]+"-"),n,++stage);
stage=localStage;
sb.delete(0,sb.capacity());
sb.append(localStr);
}
}
答案 3 :(得分:0)
import java.util.*;
/**
*
* @author BENDIABDELLAH
**/
public class Solution {
boolean boards[][];
Set<Integer> occupied_CL = new HashSet<Integer>();
Solution(int n) {
boards = new boolean[n][n];
}
Solution() {
}
void setBoard(boolean[][] boards) {
this.boards = boards;
for (int i = 0; i < boards.length; ++i) {
for (int j = 0; j < boards.length; ++j) {
if (boards[i][j]) {
occupied_CL.add(j);
}
}
}
}
int waysToPlace(int k) {
if (k == boards.length - 1) {
return 1;
}
int totalWays = 0;
for (int pos = 0; pos < boards.length; ++pos) {
int ways = 1;
if (!isAttack(k + 1, pos)) {
boards[k + 1][pos] = true;
occupied_CL.add(pos);
ways *= waysToPlace(k + 1);
boards[k + 1][pos] = false;
occupied_CL.remove(pos);
} else {
ways = 0;
}
totalWays += ways;
}
return totalWays;
}
boolean isAttack(int row, int col) {
if (occupied_CL.contains(col)) {
return true;
}
if ((col > 0 && row > 0 && boards[row - 1][col - 1]) || (col < boards.length - 1 && row > 0 && boards[row - 1][col + 1])) {
return true;
}
return false;
}
void printArray() {
for (int i = 0; i < boards.length; ++i) {
for (int j = 0; j < boards.length; ++j) {
System.out.print(boards[i][j] + " ");
}
System.out.println();
}
}
public static void main(String args[]) {
//Solution sol = new Solution(5);
// System.out.println(sol.waysToPlace(-1));
//sol.printArray();
readInput();
}
static void readInput() {
Scanner scan = new Scanner(System.in);
int t = scan.nextInt();
for (int i = 0; i < t; ++i) {
int n = scan.nextInt();
//System.out.println(" n "+n );
int k = scan.nextInt();
// System.out.println(" k "+k );
boolean boards[][] = new boolean[n][n];
for (int row = 0; row < k; ++row) {
int col = scan.nextInt();
boards[row][col] = true;
}
Solution s = new Solution();
s.setBoard(boards);
int ways = s.waysToPlace(k - 1);
System.out.println(ways);
}
}
}