如何在Ocaml中为一组布尔变量生成一组值

时间:2019-01-13 13:13:20

标签: ocaml

比方说,我们有一个函数将一组布尔变量作为输入:bol1,bol2 ... boln。我们如何使用尽可能少的代码迭代所有可能的布尔值分配?我需要实现一个函数,该函数需要输入一组两个布尔变量以及一个包含变量的布尔表达式,并创建一个真值表。如果看我的代码,那很长。所以我想减少它。此外,我的做法似乎有些多余,因为编译器发出警告说,代码中所有匹配项| Var v2都没有使用匹配项| Var v2。

这是this link中的练习46/47:“定义一个函数table2,该函数以两个变量(指定为参数)返回给定逻辑表达式的真值表。返回值必须是三元组列表包含(value_of_a,balue_of_b,value_of_expr)。“

type bool_expr =
  | Var of string
  | Not of bool_expr
  | And of bool_expr * bool_expr
  | Or of bool_expr * bool_expr 

let table2 (v1 : string) (v2 : string ) (exp : bool_expr)= 
  let rec evaluate (bol1 : bool) (bol2 : bool) (expp : bool_expr) =
    match bol1, bol2 with
    |true, true -> (match expp with
        |Var v1 -> true
        |Var v2 -> true
        |Not q -> not (evaluate bol1 bol2 q )
        |And (q,w) -> (evaluate bol1 bol2 q) && (evaluate bol1 bol2 w)
        |Or (q, w) -> (evaluate bol1 bol2 q) || (evaluate bol1 bol2 w))
    |true, false -> (match expp with
        |Var v1 -> true
        |Var v2 -> false
        |Not q -> not (evaluate bol1 bol2 q )
        |And (q,w) -> (evaluate bol1 bol2 q) && (evaluate bol1 bol2 w)
        |Or (q, w) -> (evaluate bol1 bol2 q) || (evaluate bol1 bol2 w))
    |false, true -> (match expp with
        |Var v1 -> false
        |Var v2 -> true
        |Not q -> not (evaluate bol1 bol2 q )
        |And (q,w) -> (evaluate bol1 bol2 q) && (evaluate bol1 bol2 w)
        |Or (q, w) -> (evaluate bol1 bol2 q) || (evaluate bol1 bol2 w))
    |false, false -> (match expp with
        |Var v1 -> false
        |Var v2 -> false
        |Not q -> not (evaluate bol1 bol2 q )
        |And (q,w) -> (evaluate bol1 bol2 q) && (evaluate bol1 bol2 w)
        |Or (q, w) -> (evaluate bol1 bol2 q) || (evaluate bol1 bol2 w))
  in [(true,true, (evaluate true true exp));(true,false, (evaluate true false exp));(false,true, (evaluate false true exp));(false,false, (evaluate false false exp))]

以下是预期输出的示例:

table2“ a”“ b”(And(Var“ a”,Or(Var“ a”,Var“ b”))));

  • :(布尔*布尔*布尔)列表= [(true,true,true); (正确,错误,正确); (假,真,假); (假,假,假)]

2 个答案:

答案 0 :(得分:0)

提示:尝试递归地查看问题。

bool_values { b_0, b_1, .... b_n } =
  { T + bool_values { b_1. ... b_n } } +
  { F + bool_values { b_1. ... b_n } }

答案 1 :(得分:0)

如果您不匹配bol1和bol2,而只是使用它们,则可以将代码缩减4倍。

(match expp with
   | Var v1 -> bol1
   | Var v2 -> bol2
   ...

第二次匹配不比较变量,而是比较结构。与Var v1匹配会将expp具有的值绑定到新变量v1。两种情况Var v1Var v2具有相同的结构,而第二种情况则永远不会达到。

要比较值,您必须编写:

| Var v when v == v1 -> bol1
| Var v when v == v2 -> bol2
| Var v -> (* neigther v1 nor v2, what to do now? *)

要将其扩展到具有更多列的表,您将必须使用递归,并且使用列表或数组而不是元组。例如。 type table = ((bool list) * bool) list