繁体   English   中英

找出两个皇后在n * n棋盘上相交(不稳定)的方式?

[英]Find out the Number of ways in which two queens intersects (won't be stable) on n*n chessboard?

我可以使用组合来做到这一点。 如果皇后区处于同一位置,它们将不稳定 (受到攻击):

  1. 垂直
  2. 卧式
  3. 对角线。

所以

  1. 其可能的方式为: n * P(n,2)
  2. 其可能的方式为: n * P(n,2)
  3. 其可能为: 2 * ( P(n,2) + P(n-1,2) + ... + P(2,2)) + 2 * (P(n-1,2) + ... + P(2,2))

对于上述情况,什么是合适的算法?

class Main
{
    public static void main (String[] args) throws java.lang.Exception
    {
        int n = 8;
        int arr[][] = new int[n][n];
        long x = 0;
        for (int i=0;i<n;i++){
            for (int  j=0;j<n;j++){

                x +=  Math.min(n-1-i, n-1-j) + Math.min(i, j) + Math.min(n-1-i,j) + Math.min(i,n-1-j);

                x+= 2*n -2;
            }
        }

        System.out.println(x);
     }
}

上面的逻辑怎么样?

好吧,对于n * n板,有

 All:      n * n * (n * n - 1) / 2
 Stable:   n * (n - 1) * (n - 2) * (3 * n - 1) / 6
 Unstable: n * (5 * n - 1) * (n - 1) / 3

职位。 (有关详细信息,请参见https://oeis.org/A036464 )。 n的一些示例:

 n   all   unstable   stable
-----------------------------  
 1     0 =        0  +     0
 2     6 =        6  +     0
 3    36 =       28  +     8
 4   120 =       76  +    44
 5   300 =      160  +   140
 6   630 =      290  +   340
 7  1176 =      476  +   700
 8  2016 =      728  +  1288
 9  3240 =     1056  +  2184
10  4950 =     1470  +  3480

实现(Java)很明显

private static long unstableCount(long n) {
  return n * (5 * n - 1) * (n - 1) / 3;
}

可能有趣的是,

 All      = O(n**4)
 Stable   = O(n**4)
 Unstable = O(n**3) // just cube

因此,对于大板,几乎所有位置都是稳定的。

如果皇后区分开来 (例如,您有白色红色皇后区),您要做的就是上面的数字和公式乘以 2 (交换皇后区将带来一个新的位置)。

private static long unstableDistinguishableCount(long n) {
  return n * (5 * n - 1) * (n - 1) / 3 * 2;
}

编辑 :天真的采样实现(我们循环所有可能的皇后位置)

private static long unstableCountNaive(int n) {
  long result = 0;

  for (int file1 = 0; file1 < n; ++file1)
    for (int rank1 = 0; rank1 < n; ++rank1)
      for (int file2 = file1; file2 < n; ++file2)
        for (int rank2 = file1 == file2 ? rank1 + 1 : 0; rank2 < n; ++rank2)
          if ((file1 == file2) ||                  // Same file 
              (rank1 == rank2) ||                  // Same rank
              (file1 + rank1 == file2 + rank2) ||  // Same top-left bottom-right diagonal
              (file1 - rank1 == file2 - rank2))    // Same bottom-left top-right diagonal
            result += 1;

  return result;
} 

编辑2 :如果我的想法正确,则可以只计算对角线攻击,然后使用对称性:

private static long unstableCountBetter(int n) {
  long result = 0;

  // Attacked by top-left bottom-right diagonal 
  for (int rank = 0; rank < n; ++rank)
    for (int file = 0; file < n; ++file)
      result +=
        (rank + file >= n ? 2 * n - 2 - (rank + file) : rank + file);

  result = 
    // symmetry: we have TWO diagonals
    result * 2 +       
    // At each postion (n * n of them) we have n - 1 checks on the same rank
    n * n * (n - 1) +
    // At each postion (n * n of them) we have n - 1 checks on the same file
    n * n * (n - 1);

  // /2 if queens are indistiguished (728 for 8x8 board)
  return result / 2;
} 

这个问题有点不完整,但是看评论,我想我已经掌握了所有信息来回答这个问题。

由于您写道2个皇后在3 * 3板上有56种相交的方式,因此您将两个皇后视为不同,即。 下令。 例如。 这两个板不同:

..q     ..Q
.Q.     .q.
...     ...

因此,您的问题的答案是n * n板的简单公式:

(n*n) * (n*n - 1) - n*(n-1)*(n-2)*(3*n-1)/3

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM