DeepSeek辅助总结postgresql wiki提供的数独求解器

原文地址:https://wiki.postgresql.org/wiki/Sudoku_solver
数独求解器

兼容的 PostgreSQL 版本

9.0+

编写语言

SQL

依赖项

这是我编写的一个不算特别快的数独求解器。输入格式为:'_' 代表空单元格,而 'b' 到 'j' 代表数字 1...9。棋盘以列优先顺序存储,这意味着字符串的前 9 个字符编码了第一列(从上到下),随后的 9 个字符是第二列,依此类推。

提示:你可以通过使用 ksudoku 保存游戏来创建新的数独谜题。

sql 复制代码
with recursive board(b, p) as (
  -- 以列优先顺序表示的数独棋盘,因此可以使用 substr() 来获取某一列
  values ('__g_cd__bf_____j____c__e___c__i___jd__b__h___id____e__g__b__f_e_f____g____j_h__c_'::char(81), 0)
  union all select b, p from (
    -- 生成候选棋盘:
    select overlay(b placing new_char from strpos(b, '_') for 1)::char(81), strpos(b, '_'), new_char
    from board, (select chr(n+ascii('b')) from generate_series(0, 8) n) new_char_table(new_char)
    where strpos(b, '_') > 0
  ) r(b, p, new_char) where
    -- 确保新字符在其列中不重复出现
    -- (有两个检查,因为我们要排除 p 自身的位置):
    strpos(substr(b, 1+(p-1)/9*9, (p-1)%9), new_char) = 0 and
    strpos(substr(b, p+1, 8-(p-1)%9), new_char) = 0 and
    -- 确保新字符在其行中不重复出现:
    new_char not in (select substr(b, 1+i*9+(p-1)%9, 1)
                     from generate_series(0, 8) i
                     where p <> 1+i*9+(p-1)%9) and
    -- 确保新字符在其所在的 3x3 宫内不重复出现:
    new_char not in (select substr(b, 1+i%3+i/3*9+(p-1)/27*27+(p-1)%9/3*3, 1)
                     from generate_series(0, 8) i
                     where p <> 1+i%3+i/3*9+(p-1)/27*27+(p-1)%9/3*3)
) select
    -- 以下子查询用于以 '\n' 分隔的人类可读格式表示棋盘:
    ( select string_agg((
        select string_agg(chr(ascii('1')+ascii(substr(b, 1+y+x*9, 1))-ascii('b')), '') r
        from generate_series(0, 8) x), E'\n')
      from generate_series(0, 8) y
    ) human_readable,
    b board,
    p depth,
    (select count(*) from board) steps
  from board where strpos(b,'_') = 0 limit 5000;

此示例展示了如何使用递归公共表表达式(Recursive CTE)来通用地编码任何回溯算法,步骤如下:

  1. 将初始情况置于递归 CTE 的 union 之前。
  2. UNION 之后,放置一个生成下一个可能候选值的查询。在此查询中,你将读取递归 CTE;请确保仅读取未完成的候选方案,方法是在该查询的 where 子句中指定此条件。
  3. 你可以(并且很可能应该)剪除无效的候选方案,方法是将生成候选值的子查询包裹在另一个子查询中,并使用剪除条件进行过滤。剪枝很重要,不仅是为了速度,还因为 PostgreSQL 会存储此查询返回的每一行(所有候选解),直到不再需要为止,你可能会用尽磁盘空间(尽管在 PostgreSQL 9.2+ 中,你可以使用 temp_file_limit 限制该空间,或者使用单独的临时表空间)。
  4. 最后,在最外层,递归 CTE 表中将提供所有候选方案。如本例所示,如果你剪除了所有无效的候选方案,那么所有完整的候选方案也将是有效的解。

可能的状态空间将按广度优先搜索进行处理。

相关推荐
yaoyouzhong42 分钟前
MySQL 批量插入详解:快速提升大数据导入效率的实战方法
大数据·数据库·mysql
NineData1 小时前
NineData V5.0 产品发布会:让 AI 成为数据管理的驱动力,4月16日!
数据库·人工智能·ai编程
高梦轩2 小时前
PG数据库
数据库·oracle
云草桑2 小时前
DBA mssql 解决排序规则冲突 QA prod 和开发配置都是一样的服务器排序规则 为啥开发环境的的存储过程需要 加这个COLLATE Chinese_PRC_CI_AS
数据库·dba·mssql
卤炖阑尾炎2 小时前
MySQL 故障排查与生产环境优化实战指南
数据库·mysql
小陈工2 小时前
2026年4月2日技术资讯洞察:数据库融合革命、端侧AI突破与脑机接口产业化
开发语言·前端·数据库·人工智能·python·安全
solihawk3 小时前
分区大表统计信息不准确引发的性能问题
数据库
百结2143 小时前
postgresql日常运用
数据库·postgresql·oracle
前进的李工4 小时前
MySQL大小写规则与存储引擎详解
开发语言·数据库·sql·mysql·存储引擎
CoovallyAIHub4 小时前
Sensors 2026 | 从无人机拍摄到跑道缺陷地图,机场巡检全流程自动化——Zadar机场全跑道验证
数据库·架构·github