21、证明除了1阶拉丁方外,不存在奇数阶的反对角拉丁方,然后说明如何修改拉丁方生成过程(LatinSquare)以得到反对角拉丁方生成过程(AntidiagonalLatinSquare),该过程可用于生成任意阶n的所有反对角拉丁方。
只有奇数阶方阵的对角线在中心方格相交。因此,方阵的四个角应该相同,这就禁止了除1阶方阵之外的任何方阵成为拉丁方,因为四个角不重合但包含相同的值。
为了只得到反对角拉丁方,一种解决方案是修改过程 LatinSquare ,在 for 循环开始后引入与函数 Satisf 相关的条件语句,形式为:
CorrectNWSEDiag(r, c, j) and CorrectSWNEDiag(r, c, j)
22、数独游戏:游戏目的是用数字填充一个九宫格正方形,该正方形被细分为同样数量的边长为三的相同正方形(称为区域),使得每行、每列和每个区域都恰好包含一次从 1 到 9 的数字。游戏开始时,一些数字(称为已揭示方格)已经就位。请提出一个枚举结构 X,定义其属性。关于循环变量将遍历的集合,我们能得出什么结论?
枚举结构 X 定义在笛卡尔积上,模式为 AllTI,布局类似 T2D 以体现 X 定义域的二维性质。对于循环变量 j 的集合,需排除当前行、列和所在区域已有的值,即遍历 1 到 9 中除去 X[r, 1 到 c - 1]、X[1 到 r - 1, c] 以及 X[((r - 1) / 3) * 3 + 1 到 r - 1, ((c - 1) / 3) * 3 + 1 到 c - 1] 值域的部分。
23、编写程序Sudoku1(无已揭示方块)的代码以及调用程序。大约有7×10²¹个解。估算该程序在典型当前处理器上的计算时间。
程序 Sudoku1 的代码如下:
1. procedure Sudoku1(r, c) pre
2. r ∈ 1 .. 9 and c ∈ 1 .. 9
3. begin
4. for j parcourant 1 .. 9 - codom
X[r, 1 .. c - 1] ∪ X[1 .. r - 1, c] ∪
X
r - 1
3
· 3 + 1 .. r - 1,
c - 1
3
· 3 + 1 .. c - 1
do
5. X[r, c] ← j;
6. if r = 9 and c = 9 then
7. write(X)
8. else
9. if c = 9 then
10. Sudoku1(r + 1, 1)
11. else
12. Sudoku1(r, c + 1)
13. end if
14. end if
15. end for
16. end
调用程序如下:
1. variables
2. X ∈ 1 .. 9 × 1 .. 9 → 1 .. 9
3. begin
4. Sudoku1(1, 1)
5. end
粗略的实验评估估计该程序的执行时间约为 190亿年 ,这超过了通常认为的宇宙年龄!
24、在大多数实际使用的编程语言中,不具备遍历一个不完整区间(带有“空洞”)的特性。假设之前有一个Sudoku1过程利用了该特性,现在基于此修改Sudoku1过程以得到一个高效版本的Sudoku2(建议避免在X内部进行顺序搜索)。
为了提高效率,定义一个由三个布尔表 H 、 V 和 R 组成的数据结构(其属性强化了现有不变量),通过直接访问快速给出答案。具体而言:
-
H[r, j](分别地,V[j, c])为真,当且仅当值j未在第r行(分别地,第c列)中使用。 -
R[r, c, j]为真,当且仅当j未在包含方格(r, c)的区域中使用。
以下是 Sudoku2 过程代码:

最低0.47元/天 解锁文章
2453

被折叠的 条评论
为什么被折叠?



