| (true,Select(true)) => true
| (false,Select(false)) => false
如何在具有通用类型的switch语句中结合这两者?
| (true,Select(true)) => true
| (false,Select(false)) => false
如何在具有通用类型的switch语句中结合这两者?
不幸的是,您在 switch 语句中匹配的模式必须是“线性的”(即,模式内的变体应该只出现一次):
见https://caml.inria.fr/pub/docs/oreilly-book/html/book-ora016.html
模式必须是线性的,也就是说,在匹配的模式中,任何给定的变量都不能出现多次。因此,我们可能希望能够编写:
# let equal c = match c with
(x,x) -> true
| (x,y) -> false;; Characters 35-36: This variable is bound several times in this matching
但这需要编译器知道如何执行 平等测试。然而,这立即引发了许多问题。要是我们 接受值之间的物理平等,我们得到一个系统 弱,无法识别两次出现的相等性 列表 [1; 2],例如。如果我们决定使用结构平等, 我们冒着必须遍历、无限循环、循环的风险 结构。
请注意,ReasonML 只是 OCaml 的替代语法,因此上述内容也适用于 Reason。 match
只是 switch
的 OCaml 版本。
可以使用 when
守卫一般地将这两种情况结合起来:
let f = (a,b) =>
switch (a,b) {
| (a,Select(b)) when a == b => a
};
但是,请注意这并不是详尽无遗的,您还没有指定在 a != b
的情况下应该返回什么。为避免非穷尽性警告和运行时崩溃,您需要添加另一个案例来涵盖这一点。
是的,这是可行的:
// using switch
let theSolution = x => switch(x) {
| (_,Select(inside)) => inside
};
// using `fun`
let theSolution = x => x |> fun | (_,Select(inside)) => inside;
// or for a super short solution:
let theSolution = fun | (_,Select(inside)) => inside;
例如:
type select = | Select(bool);
let a = (true,Select(true));
let b = (true,Select(false));
let c = (false,Select(true));
let d = (false,Select(false));
let theSolution = x => x |> fun | (_,Select(inside)) => inside;
Js.log2("A is",theSolution(a));
Js.log2("B is",theSolution(b));
Js.log2("C is",theSolution(c));
Js.log2("D is",theSolution(d));
将导致:
"A is" true
"B is" false
"C is" true
"D is" false
或者,如果要比较布尔值,可以执行以下任一操作:
let theSolution = fun | (a,Select(b)) => a && b;
let theSolution = fun | (a,Select(b)) => a == b;
See this example in the online repl
,关注可以解决您的问题。 a && b 操作取决于您希望该块遵循的逻辑。我合理地假设您要执行AND运算。如果您提供其他可能的条件,则可以对其进行完善。
let getSelectionResponse = x => switch(x){ | (a,Select(b)) => a&&b};