用于跟踪OCaml中游戏板的数据结构

use*_*201 6 arrays ocaml

我是OCaml的新手,我想要实现一个类似于四线的游戏.我需要的是一些保持游戏状态的数据结构.游戏板是一个4x4的正方形,共有16块瓷砖.我正在寻找OCaml中的表示,这将使得在整个列,行或对角线中检索(或执行某些操作)所有元素变得容易和快速.我将在这个游戏上进行极小极大搜索,这就是为什么速度很重要.

到目前为止,我已经考虑过一维列表.列表的问题在于难以弄清楚哪些元素属于每个行/列/对角线,然后使用List.map例如检索它们.

我想过要用Array.make 4 (Array.make 4 Empty);;.这对于行来说绝对是完美的.很容易得到它们并在其上进行模式匹配.但是在单个列和对角线上进行模式匹配是一件苦差事.

我想要做的是有一个功能,它采用游戏板并返回包含所有行/列/对角线的列表.我想做,例如,match (rows,columns,diagonals) with (Empty, Empty, Empty, Empty) -> something.

did*_*erc 1

有时匹配不起作用。在这里,我认为您应该尝试尽可能多地使用函数,然后让单元格先行或先列不会那么复杂,您甚至可以通过反转索引顺序从一种表示移动到另一种表示。

如果我使用以下类型:

type color = Red | Yellow;;
type cell  = Empty | Color of color;;
type board = Array.make 4 (Array.make 4 Empty);;
Run Code Online (Sandbox Code Playgroud)

并首先决定列,然后以下函数将获得行或列:

let column (b: board) i j = b.(i).(j)
let row (b: board) i j = b.(j).(i)
Run Code Online (Sandbox Code Playgroud)

对于对角线,有两组,一组从左上到右下,另一组沿另一个方向(从右上到左下):

let ldiag (b: board) i j = b.((i + j) mod 4).(j)
let rdiag (b: board) i j = b.((i - j + 4) mod 4).(j)
Run Code Online (Sandbox Code Playgroud)

然后我猜想检查行、列或对角线只需检查该行的 4 个单元格即可。

let check predicate linef k = predicate (linef b k 0) && 
                               predicate (linef b k 1) && 
                               predicate (linef b k 2) && 
                               predicate (linef b k 3)
Run Code Online (Sandbox Code Playgroud)

例如,检查是否有红色对角线:

let has_line linef b color = 
    let cmp x = x = color in
    let check k = check cmp linef b k in
    check 0 || check 1 || check 2 || check 3

let has_ldiag b color = has_line ldiag b color
let has_rdiag b color = has_line rdiag b color

let has_red_diagonal b = has_ldiag b Red | has_rdiag b Red
Run Code Online (Sandbox Code Playgroud)

ETC。