【问题标题】:Sudoku solver, not backtracking solver [closed]数独求解器,而不是回溯求解器 [关闭]
【发布时间】:2014-06-22 18:51:17
【问题描述】:

过去几周我一直在开发数独游戏。 游戏作为很多功能,如:玩游戏,打印数独,解决数独。

求解函数使用传统的回溯,但这不是问题,问题是我需要游戏能够产生人道可解的数独,因为我需要一种能够像人类一样解决数独的方法会做的。

如果有人能帮我弄清楚如何做到这一点,我将不胜感激。

【问题讨论】:

  • 如果我们知道您的代码是什么,那将会很有用。您是使用纯回溯(通常称为蛮力)还是有一个逻辑求解算法仅将回溯用作最后手段?
  • 如果数独(所有人都应该)有一个独特的解决方案,则该解决方案可以通过纯逻辑解决,也可以由人类解决。那么你真正在寻找什么?
  • 你不能只创建一个遵循数独规则的随机矩阵,然后随机删除一个数字,使用回溯器解决它以确保存在一个解决方案并且它是唯一的,如果它是可解决的然后你删除另一个并重复,直到没有解决方案或解决方案不是唯一的,然后你只保留以前的数独。我认为这将是 O(n^3)?
  • @k_g 我有一个使用标准回溯(蛮力)的求解方法,但我需要的是一种使用你提到的逻辑求解算法的方法。
  • @DonRoby Don Roby,是的,普通数独是可以解决的,但如果您随机删除错误的数字,则无法使用通用逻辑解决。

标签: java sudoku


【解决方案1】:

在Andrew Stuart's Sudoku page 上很好地展示并解释了人类玩家的大量数独解决策略:

**Show Possibles**         
1: Hidden Singles      
2: Naked Pairs/Triples     
3: Hidden Pairs/Triples    
4: Naked Quads     
5: Pointing Pairs      
6: Box/Line Reduction      
**Tough Strategies**  
7: X-Wing      
8: Simple Colouring        
9: Y-Wing      
10: Sword-Fish         
11: XYZ Wing       
**Diabolical Strategies** 
12: X-Cycles       
13: XY-Chain       
14: 3D Medusa      
15: Jelly-Fish         
16: Unique Rectangles      
17: Extended Unique Rect.      
18: Hidden Unique Rect's       
19: WXYZ Wing      
20: Aligned Pair Exclusion         
**Extreme Strategies**    
21: Grouped X-Cycles       
22: Empty Rectangles       
23: Finned X-Wing      
24: Finned Sword-Fish      
25: Altern. Inference Chains   
26: Sue-de-Coq         
27: Digit Forcing Chains       
28: Nishio Forcing Chains  
29: Cell Forcing Chains        
30: Unit Forcing Chains        
31: Almost Locked Sets         
32: Death Blossom      
33: Pattern Overlay Method         
34: Quad Forcing Chains        
**"Trial and Error"** 
35: Bowman's Bingo

作为一个相当频繁的玩家,我会将策略 11 之外的所有内容都判断为“不再有趣”。但这可能是一个品味问题。

【讨论】:

    【解决方案2】:

    如果你只需要一个快速的随机数独,你可以使用一种特殊的方式来创建一个有效的数独模式,下面是我不久前想出的算法:

    You initialize an array with a randomized set of the numbers 1 to 9, 
    technically it's easier if you initialize 3 arrays each with 3 length.
    You can have these numbers be randomized, thus create a different sudoku.
    
    [1 2 3] [4 5 6] [7 8 9]
    Then you shift these:
    [7 8 9] [1 2 3] [4 5 6]
    [4 5 6] [7 8 9] [1 2 3]
    
    Then you shift the numbers inside the arrays:
    
    [3 1 2] [6 4 5] [9 7 8]
    Then you shift the arrays themselves again:
    [9 7 8] [3 1 2] [6 4 5]
    [6 4 5] [9 7 8] [3 1 2]
    
    Then you shift the numbers inside the arrays:
    
    [2 3 1] [5 6 4] [8 9 7]
    Then you shift the arrays again:
    [8 9 7] [2 3 1] [5 6 4]
    [5 6 4] [8 9 7] [2 3 1]
    

    你将拥有最后一组数独表:

    [1 2 3] [4 5 6] [7 8 9]
    [7 8 9] [1 2 3] [4 5 6]
    [4 5 6] [7 8 9] [1 2 3]
    [3 1 2] [6 4 5] [9 7 8]
    [9 7 8] [3 1 2] [6 4 5]
    [6 4 5] [9 7 8] [3 1 2]
    [2 3 1] [5 6 4] [8 9 7]
    [8 9 7] [2 3 1] [5 6 4]
    [5 6 4] [8 9 7] [2 3 1]
    

    这是有效的。之后,您可以取出一些数字,然后您可以检查您已经拥有的算法是否有一个解决方案或多个解决方案。如果删除某个数字会产生多个,请撤消它并结束删除,或者尝试删除另一个。

    【讨论】:

    • 我已经有了一个算法,可以产生我要求的任何随机数独板,都是有效的数独板。
    • 哦,好吧,我以为这就是你要找的。所以你已经有了有效的板,但你需要一种方法来删除数字并保持它的可解性。除了随机挑选数字并检查有多少解决方案,如果只有一个解决方案则继续删除,如果没有则撤消删除并尝试另一个是我目前能想到的唯一方法。跨度>
    • 另外,我有一种方法可以通过董事会以指定的百分比删除随机数(删除数字的几率为 50%)。我需要的是一个示例或说明如何验证生成的谜题是否可以人工解决,这意味着蛮力(回溯)在这里没有用。
    • 除了某种形式的聪明的迭代暴力破解,我不确定你能做什么。
    • 从技术上讲,如果您在给定状态下维护给定单元格的可用数字列表并将这些列表迭代为暴力破解,它会显着减少您需要检查的尝试次数(从 9^n 开始) .
    猜你喜欢
    • 2023-03-27
    • 2017-12-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-12-11
    • 2014-02-07
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多