【问题标题】:Haskell: Get block for Sudoku solverHaskell:获取数独求解器的块
【发布时间】:2011-01-31 14:07:58
【问题描述】:

我正在尝试为我正在进行的项目构建数独求解器。我有一个 9x9 网格,每个位置编号为 0..80,从左到右,从上到下

例如:

0 1 2 3 4 5 6 7 8

9 10 ...

我正在尝试返回一个 Int 列表,该列表表示某个位置所在的 3x3 网格。例如,对于位于网格 (0,0) 中的位置 1,它将返回 [0,1,2,9, 10,11,18,19,20],对于位于网格 (0,2) 中的位置 8,它将返回 [6,7,8,15,16,17,24,25,26]。

我编写了一个函数,它在 9x9 数独上返回所需的 3x3 网格:

getBlock :: Int -> Int -> [[Int]]
getBlock x y = [[((x * sudokuSizeSq + 0) * sudokuSize) + (y * sudokuSizeSq + 0),((x * sudokuSizeSq + 0) * sudokuSize) + (y * sudokuSizeSq + 1)..((x * sudokuSizeSq + 0) * sudokuSize) + (y * sudokuSizeSq + (sudokuSizeSq-1))],[((x * sudokuSizeSq + 1) * sudokuSize) + (y * sudokuSizeSq + 0),((x * sudokuSizeSq + 1) * sudokuSize) + (y * sudokuSizeSq + 1)..((x * sudokuSizeSq + 1) * sudokuSize) + (y * sudokuSizeSq + (sudokuSizeSq-1))],[((x * sudokuSizeSq + 2) * sudokuSize) + (y * sudokuSizeSq + 0),((x * sudokuSizeSq + 2) * sudokuSize) + (y * sudokuSizeSq + 1)..((x * sudokuSizeSq + 2) * sudokuSize) + (y * sudokuSizeSq + (sudokuSizeSq-1))]]

在哪里: sudokuSizeSq 是宽度的平方 (3) sudokuSize 是宽度 (9)

x 和 y 表示可能的网格。

这可行,但我想增加它,以便它适用于更大的网格。我将代码更改为以下,但似乎不会加载该函数。

getBlock :: Int -> Int -> [[Int]]
getBlock x y = [[((x * sudokuSizeSq + 0) * sudokuSize) + (y * sudokuSizeSq + 0),((x * sudokuSizeSq + 0) * sudokuSize) + (y * sudokuSizeSq + 1)..((x * sudokuSizeSq + 0) * sudokuSize) + (y * sudokuSizeSq + (sudokuSizeSq-1))],[((x * sudokuSizeSq + 1) * sudokuSize) + (y * sudokuSizeSq + 0),((x * sudokuSizeSq + 1) * sudokuSize) + (y * sudokuSizeSq + 1)..((x * sudokuSizeSq + 1) * sudokuSize) + (y * sudokuSizeSq + (sudokuSizeSq-1))]..[((x * sudokuSizeSq + (sudokuSizeSq-1)) * sudokuSize) + (y * sudokuSizeSq + 0),((x * sudokuSizeSq + (sudokuSizeSq-1)) * sudokuSize) + (y * sudokuSizeSq + 1)..((x * sudokuSizeSq + (sudokuSizeSq-1)) * sudokuSize) + (y * sudokuSizeSq + (sudokuSizeSq-1))]]

我这样做的方式似乎很麻烦,有没有更好的方法来做到这一点或解决我遇到的问题的方法。谢谢。

【问题讨论】:

    标签: haskell


    【解决方案1】:
    [ a + b
    | a <- take sudokuSizeSq $ map (sudokuSize *) [x * sudokuSizeSq .. ]
    , b <- take sudokuSizeSq [y * sudokuSizeSq ..] ]
    

    【讨论】:

    • 这几乎给出了正确的结果。但是,如果我将 x 设为 1,将 y 设为 0,它会返回 [9,10,11,18,19,20,27,28,29],而它应该返回 [27,28,29,36,37, 38,45,46,47]
    • @Joseph:是的,我错了。几乎?好奇哪一部分是关闭的。
    • 抱歉 - 按回车键,它在我完成之前提交了我的评论 - 我已经在上面进行了编辑。
    • @Joseph:啊,只是跳得不够远。嗯,这很容易解决。
    • 完美。谢谢你。如果您有机会,您能否简要解释一下它在做什么,我特别不确定 take sudokuSizeSq 位的作用。如果您没有时间,请不要担心。
    【解决方案2】:

    您可以遍历每个块中的 x/y 偏移量以生成其中的所有位置。列表推导使这变得相当容易:

    getBlock :: Int -> Int -> [[Int]]
    getBlock x y = [[(y*sudokuSizeSq+dy)*sudokuSize + x*sudokuSizeSq+dx | dx <- offsets]
                    | dy <- offsets]
        where offsets = [0..sudokuSizeSq-1]
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2012-03-10
      • 1970-01-01
      • 2014-06-06
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2023-03-27
      • 2013-03-08
      相关资源
      最近更新 更多