暴力迫使大脑拼图

时间:2012-10-23 19:32:13

标签: performance algorithm puzzle

我从lonpos.cc获得了一个大脑之谜作为礼物。我很清楚有多少不同的解决方案,我非常喜欢编写算法和代码,所以我开始编写一个应用程序来强制它。

拼图如下:http://www.lonpos.cc/images/LONPOSdb.jpg / http://cdn100.iofferphoto.com/img/item/191/498/944/u2t6.jpg

这是一个20x14“积分”的董事会。所有拼图都可以翻转和翻转。我写了一个应用程序,其中每个部分(和拼图)都是这样呈现的:

01010
00100
01110
01110
11111
01010

现在我的申请到目前为止相当简单。

它需要一个片段列表和一个空白板,片段#0的弹出窗口 将它翻转到每个方向,并为该片段尝试将其放置在每个x和y坐标上。如果它成功地放置了一块它传递了一个新的“板”的副本,其中一些片段被带到一个递归函数,并尝试所有组合为他们的片段。

以伪代码解释:

bruteForce(Board base, List pieces) {
    for (Piece in pieces.pop, piece.pop.flip, piece.pop.flip2...) {
        int x,y = 0;
        if canplace(piece, x, y) {
            Board newBoard = base.clone();
            newBoard.placePiece(piece, x, y);
            bruteForce(newBoard, pieces);
        }
        ## increment x until x > width, then y
    }
}

现在我正试图找到更快的方法。到目前为止我想到的事情:

  1. 并行解决 - 已实施,现在使用4个线程。
  2. 对棋子进行分类,并且只尝试放置适合我们试图适合的x,y空间的棋子。 (如果我们在最底行,Aka,从我们的位置到底部只有4个“点”,不要尝试8个高点。)
  3. 不要复制电路板,而是使用placePiece和removePiece或类似的东西。
  4. 检查“无效”电路板,也就是说无法接触到一块(完全装箱)。
  5. 任何人对如何更快地做到这一点都有任何创意?或者以任何方式以数学方式计算出有多少种不同的组合?

2 个答案:

答案 0 :(得分:3)

我没有看到任何明显的方法来快速做事,但这里有一些可能有用的提示。

首先,如果忽略凸起,则需要一个6x4网格来填充1x2块。每个块具有6个位置,其中可以具有凸起或孔。因此,您试图找到块的排列,使得在每个边缘处,凸起与孔匹配。此外,您可以使用此信息更有效地表示作品。

接下来,我建议尝试所有方法将块放在特定位置而不是所有位置以在任何地方播放特定块。这样可以减少你失误的虚假踪迹。

答案 1 :(得分:1)

这看起来像Exact Cover Problem。你基本上想要用你给定的部分覆盖板上的所有字段。我可以推荐由Donald Knuth出版的Dancing Links。在paper中,您可以找到pentomino problem的明确示例,它可以让您了解其工作原理。

您基本上建立了一个系统,可以跟踪在电路板上放置特定块的所有可能方法。通过放置一个区块,您将覆盖场地上的一组位置。这些位置不能用于放置任何其他块。在放置另一个块之前,所有可能性都将从问题设置中删除。舞蹈链接允许快速回溯和擦除可能性。