我的教授让我们在F#中实施笛卡尔积。他正在为我们提供一种类型:
type SET =
| I of int list // I [1;2;3]
| S of string list // S ["a";"b";"c"]
| IS of (int * string) list // IS [(1, "a");(2, "b")]
| II of (int * int) list // II [(1,2); (3,4); (5,6)]
| SS of (string * string) list // SS [("a","b"); ("c","d")]
| SI of (string * int) list // SI [("a", 1); ("b", 2); ("c", 3)]
| SISI of ((string * int) * (string * int)) list // SISI [(("a", 1), ("b", 2)); (("c", 3), "d", 4))]
| SIIS of ((string * int) * (int * string)) list // SIIS [(("a", 1), (2, "b")); (("c", 3), (4, "d"))]
在这样做的过程中,我们也会获得一个'产品'功能如下:
let product s1 s2 =
match (s1, s2) with
| (I s1, I s2) -> II (pairs s1 s2)
| (S s1, S s2) -> SS (pairs s1 s2)
| (I s1, S s2) -> IS (pairs s1 s2)
| (S s1, I s2) -> SI (pairs s1 s2)
| (SI s1, IS s2) -> SIIS (pairs s1 s2)
| (SI s1, SI s2) -> SISI (pairs s1 s2)
赋值是创建一个函数' pair',它组装SET元素的笛卡尔积。我们被告知要创建一个可以在列表中分配值的函数。我在这里这样做了:
let rec dist a L =
match L with
| [] -> []
| h::t -> (a,h) :: dist a t
到目前为止,我的功能看起来像这样:
let rec pairs s1 s2 =
match s1 with
| [] -> []
| h::t -> dist h s2 // AND (pairs t s2)
我不明白我需要如何修改匹配语句的最后一行以正确反映我们想要的输出。这将成功完成部分功能,但只有第一位(与列表头分布的事实相关,但不是尾部)。如何将此函数的第一个循环的结果连接到s1'对t s2'以便第一段中创建的元素与第二段中的元素匹配,以防止预期类型发生冲突?
答案 0 :(得分:5)
对不起,这是一个非常愚蠢的问题。如果任何人都可以帮助处理类似情况,可以通过将最后一行写为:
来解决这种情况let rec pairs s1 s2 =
match s1 with
| [] -> []
| h::t -> (dist h s2) @ (pairs t s2)
我之前尝试过使用::运算符进行所有连接,但这是此操作的错误操作符类型。