我对Bejeweled游戏提出的编程挑战感兴趣。它似乎是一个简单的游戏,但从程序角度看它看起来更复杂。
在我寻找关于董事会评估方式的提示时,我遇到了简单谈话中好人们提出的this QUIZ。他们已经发布了获胜的答案,但如果我能真正了解解决方案的工作方式,我就会被涂上粉红色的羽毛。我可以看到它与矩阵有关,并将单元格值与它们的行和列分组,但这是迄今为止我所得到的。任何人都可以为我进一步打破它吗?
POSTED SOLUTION(测验的详细信息在上面的链接中):
--====== Table matches needs to be loaded only once
CREATE TABLE matches(offsetRow1 INT, offsetCol1 INT, offsetRow2 INT, ofsetCol2 INT, directions VARCHAR(20))
-- for horizontal
INSERT INTO matches VALUES(-1, -1, -1, -2, 'up')
INSERT INTO matches VALUES(-1, -1, -1, 1, 'up')
INSERT INTO matches VALUES(-1, 1, -1, 2, 'up')
INSERT INTO matches VALUES( 1, -1, 1, -2, 'down')
INSERT INTO matches VALUES( 1, -1, 1, 1, 'down')
INSERT INTO matches VALUES( 1, 1, 1, 2, 'down')
INSERT INTO matches VALUES( 0, -2, 0, -3, 'left')
INSERT INTO matches VALUES( 0, 2, 0, 3, 'right')
-- for verical
INSERT INTO matches VALUES(-2, -1, -1, -1, 'left')
INSERT INTO matches VALUES(-1, -1, 1, -1, 'left')
INSERT INTO matches VALUES( 1, -1, 2, -1, 'left')
INSERT INTO matches VALUES(-2, 1, -1, 1, 'right')
INSERT INTO matches VALUES(-1, 1, 1, 1, 'right')
INSERT INTO matches VALUES( 1, 1, 2, 1, 'right')
INSERT INTO matches VALUES(-2, 0, -3, 0, 'up')
INSERT INTO matches VALUES( 2, 0, 3, 0, 'down')
--==================================================
;WITH CTE
AS
(
SELECT
[Row] = CAST( [#] AS INT ),
[Col] = CAST( [Col] AS INT ),
[Value]
FROM bejeweled
UNPIVOT ([Value] FOR [Col] IN ([1],[2],[3],[4],[5],[6],[7],[8],[9])) unpvt
)
SELECT DISTINCT T.Row, T.Col, T.Value, directions
FROM CTE T
JOIN CTE T1
ON T.Value = T1.Value
JOIN CTE T2
ON T.Value = T2.Value
JOIN matches
ON (T1.Row - T.Row) = offsetRow1
AND (T1.Col - T.Col) = offsetCol1
AND (T2.Row - T.Row) = offsetRow2
AND (T2.Col - T.Col) = ofsetCol2
ORDER BY T.Row, T.Col
答案 0 :(得分:3)
unpivot函数将原始数据转换为线性列表而不是矩阵。例如,由于原始列中1,1的值为8,因此新表的第一行为1,1,8。同样,由于原始表的第一行的第二列是5,因此我们新表的第二行是1,2,5。
'With CTE'有效地创建了一个名为CTE的内存表,因此这个新的3列81行表称为CTE。
逻辑发生在内连接中:CTE中的每个单元都连接到CTE中值匹配的每个单元,并且再次与值匹配的单元连接。这意味着原始表中的每个单元都知道每个其他可能的三项匹配。也就是说,返回包含值“1”(例如)的3个单元格列表的每个单独排列。
让我们看看值2.在(6,2)处有一个,在(5,3)处有另一个,在(7,3)处有另一个,所以内连接的一个可能值将具有T.行为6,T.Col为2,T1.Row为5,T1.Col为3,T2.Row为7,T2.Col为3.我们通过查看交换(6,2)来知道( 6,3)将三者连成一排。但JOIN声明如何知道?
嗯,一个有效的举动就是把T放在T1和T2之间。确定我们的3组合是否满足的最简单方法是检查偏移并将其与相关位置列表进行比较。 T1在T(-1,1)的上方和右侧,T2在T(1,1)的右下方。我们检查并查看(-1,1,1,1)是否是有效匹配。它是,因此它通过了JOIN标准并保留了结果。