2n Queen question

Source: Internet
Author: User
Tags bit set

In the Blue Bridge Cup basic training problem, there are such a topic:

Problem description

Given a n*n chessboard, there are some places in the chessboard that cannot be placed in Queens. Now to put n black Queen and n White Queen in the chessboard, so that any two black queens are not on the same line, the same column or the same diagonal, any two white queens are not on the same line, the same column or the same diagonal. Q. How many kinds of methods are there in total? n is less than or equal to 8.

Input format

The first behavior of the input is an integer n, which indicates the size of the chessboard.
Next n rows, each row n 0 or 1 of integers, if an integer is 1, indicating that the corresponding position can be placed Queen, if an integer is 0, indicating that the corresponding position can not put the queen.

Output format

Outputs an integer that indicates how many methods are put in total.

Sample input

4
1 1 1 1
1 1 1 1
1 1 1 1
1 1 1 1

Sample output

2

Sample input

4
1 0 1 1
1 1 1 1
1 1 1 1
1 1 1 1

Sample output

0


Before solving the 2n queen problem, learn the most efficient algorithm for the currently recognized N Queens.

Efficient algorithm for n-Queens using bitwise operations

The core code is as follows:

void Test (int row, int ld, int rd) {int pos, p;if (row! = Upperlim) {pos = Upperlim & (~ (Row | ld | rd)); while (POS {p = pos & (~pos + 1);p OS = pos-p;test (Row | p, (LD | p) << 1, (rd | p) >> 1);}} Else++ans;}

Initialization: Upperlim = (1 << N)-1; Ans = 0;

Call Parameters: Test (0, 0, 0);

As with the normal algorithm, this is a recursive function, the program is a line to find the place to put the Queen. The function has three parameters, row, ld, and Rd, which indicate which parts of the line are not allowed to be placed under the constraints of the vertical and two diagonal directions. The conflicting locations on this line are represented by a row, LD, and a in Rd. Put them three together and get all the forbidden bits of the line, take the reverse and get all the positions that can be placed (expressed in POS).

p = pos & (~pos + 1) The result is to remove the rightmost 1. In this way, p represents a position where a child of the line can be placed, removes it from the POS and recursively calls the test procedure.

Note that the three parameters of the recursive call change, each parameter is added a forbidden bit, but the two diagonal direction of the ban on the next row of the effect needs to be shifted one bit. Finally, if the recursive to a certain time to find Row=upperlim, it means that n queens all put in, find the number of solutions plus one.

650) this.width=650; "src=" Http://hi.csdn.net/attachment/201108/3/0_1312359568zQ5V.gif "style=" border:none; "/>

650) this.width=650; "src=" Http://hi.csdn.net/attachment/201108/3/0_1312359579PKeu.gif "style=" border:none; "/>

Note:
upperlime:= (1 << N)-1 generates a binary number consisting of n 1.
This program is searched from top to bottom.
POS &-pos means to take the rightmost 1 and then make up the binary number, the equivalent of POS & (~pos + 1), because after all the number is reversed (how to listen like nonsense), plus 1, is to change the lowest bit, if the low number is 1, plus this 1 will go up To go, all the way up to 0, in doing and arithmetic is coincident with the 1 corresponding to the original number. Examples can illustrate:

Original number 0 0 0 0 1 0 0 0 Original 0 1 0 1 0 0 1 1

Take reverse 1 1 1 1 0 1 1 1 take reverse 1 0 1 0 1 1 0 0
Plus 1 1 1 1 1 1 0 0 0 plus 1 1 0 1 0 1 1 0 1

   and operations     0 0 0 0 1 0 0 0    and  0 0 0 0 0 0 0 1
      in which, the inverse plus 1 is the complement, and operation and negative, that is, bitwise and complement and operation.
        (LD | p) << 1 is because the placeholder caused by LD is shifted to the right in the next line;
        (RD | p) >> 1 is because the placeholder caused by Rd is shifted to the left in the next row.
        ld Rd Row also wants to work with upperlime , and the result is that the number of n is valid from the lowest number of digits. The reason is that in the last operation the LD shifted to the right, and if not, it would mistakenly place the position outside of N as a valid bit.
        POS has finished the task and is subtracting p because?
        while loop because?
        When we go to a certain level of search, POS stores all the available locations, in order to find all the solutions, must traverse all the places to be put, and every passing point must be deleted, Otherwise it's a dead loop!

This is currently recognized as the most efficient algorithm of n queens.

(The above content originates from the blog http://blog.csdn.net/hackbuteer1/article/details/6657109)

This algorithm solves the N queen problem so cleverly. However, the 2n queen problem has two more restrictions than this:

1, n*n the Black queen and the White Queen each n, any two same color queen can not be in the same row, the same column or the same diagonal, and the same position only a queen;

2, there are several places in the chessboard can not put any queen (number and position random);

Conditions are not harsh, by now recognized N Queen's most efficient algorithm slightly modified can solve the problem.

At this point, you may have two questions:

1, in each row, if the two queens can place the preferred location conflict, how to resolve? Is it possible to ensure that the two queens are placed in this position statistically?

2, how to filter out the condition 2 of these prohibited bits?

/* **  currently the fastest 2N Queen recursive solution  ** 2N Queens Problem **  heuristic-backtracking algorithm, recursive implementation **  Adapted according to HTTP://BLOG.CSDN.NET/HACKBUTEER1/ARTICLE/DETAILS/6657109 * * #include  <stdio.h> #include  < Stdlib.h> #define  MAXN32long sum = 0, upperlim = 1, wall[MAXN]  The = {0};//  heuristic algorithm starts with the rightmost column.   void blackwhitequeen (int line, long row1, long ld1, long  RD1,&NBSP;LONG&NBSP;ROW2,&NBSP;LONG&NBSP;LD2,&NBSP;LONG&NBSP;RD2) {long pos1, pos2, p1, p2; if (row1 != upperlim | |  row2 != upperlim) {// row,ld,rd for the "or" operation, to find all the columns that can be placed in the Queen, the corresponding bit is 0,           //  then take the inverse "and" on the full 1 of the number, to find the current all can place the Queen position, the corresponding column changed to 1           //  is to find out which columns are currently available to place Queen   pos1 = upperlim & ~ ( ROW1&NBSP;|&NBSP;LD1&NBSP;|&NBSP;RD1)  & ~wall[linE];while (POS1)// 0 --  Queen has no place to put, backtrack   {//  copy pos rightmost 1 bit, rest bit set 0               //  is to get the rightmost column that can put the Queen   p1  = pos1 & -pos1;//  0          for POS rightmost 1       //  to get ready for the next right-most available column use,        The        //  program will go back to this position in the future to test pos1 -= p1;pos2 =  upperlim & ~ (ROW2&NBSP;|&NBSP;LD2&NBSP;|&NBSP;RD2)  & ~wall[line] & ~ P1;while (Pos2) {p2 = pos2 & -pos2;pos2 -= p2;// row + p, placing the current column 1 That records the column the Queen placed.               //  (LD&NBSP;+&NBSP;P)  << 1, mark the current queen left adjacent column does not allow the next queen to be placed.               //  (ld + p)  >> 1, which marks the current queen right adjacent to the column does not allow the next queen to be placed.               //  The shift operation here is actually the limit on the diagonal, just because the problem is attributed to                //  is resolved on a grid of rows, so the limit for the column is yes. Obviously, with shift               //  before each column selection, Originally nxn a placed Queen in the grid against its diagonal               // The restrictions on   have been recorded   blackwhitequeen (line + 1, row1 + p1,  (ld1 + &NBSP;P1)  << 1,  (RD1&NBSP;+&NBSP;P1) &NBSP;&GT;&GT;&NBSP;1,&NBSP;ROW2&NBSP;+&NBSP;P2,   (LD2&NBSP;+&NBSP;P2)  << 1,  (RD2&NBSP;+&NBSP;P2)  >> 1);  }} elsesum++;} Blackwhitequeenint main (int argc, char const *argv[]) {int n = 8, &NBSP;I,&NBSP;D;SCANF ("%d", &Nbsp;&n);//  because of the limit of the integer number, the maximum can only be 32 bit,      //  if you want to handle the queen problem of n greater than 32, need        //  storage with BITSET data structure   if ((n < 1)  | |   (n > 32)) {printf ("can only calculate between 1~32 \ n"); exit (-1);}  n a Queen needs n-bit storage, and a queen in a column in n column corresponds to bit 1.  upperlim =  (upperlim << n)  - 1;for  (i = 0; i  < n * n; ++i) {scanf ("%d",  &d); if (d == 0) wall[i / n]  |= 1 <<  (i % n);} Blackwhitequeen (0, 0, 0, 0, 0, 0, 0);p rintf ("%d",  sum); return 0;}

A question for the correct backtracking algorithm is completely a cinch.

It is important to note that when calculating the P2, when the position of the White Queen in the current row is calculated P1

Pos2 = Upperlim & ~ (Row2 | ld2 | rd2) & ~wall[line] & ~p1;

Cannot be written

Pos2 = (Upperlim & ~ (Row2 | ld2 | rd2) & ~wall[line])-p1;//or Pos2 = (Upperlim & ~ (Row2 | ld2 | rd2))-Wall[l INE]-P1;

When the two queens can be placed in the preferred position not at the same time, the latter is clearly wrong to draw the Pos2.

The reason pos1-= P1 is correct because the bit pos1 corresponding to ' 1 ' in P1 is ' 1 '. But Pos2 is not necessarily.

And for question 2, here refer to row, LD, RD These three parameters of the practice, wall[] array, the first n valid, Wall[k] in the binary number of the "1" bit represents this position in the K row can not put queen.

This article is from the "Alan Digest Blog" blog, reproduced please contact the author!

2n Queen question

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.