我有一个"子状态":
type SubState =
| DoingA
| DoingB
| AFewMore
和一个主要状态:
type State =
| Initializing
| DoingStuff of SubState
| DoingNothing
然后我在匹配语句中使用该状态:
let state : State = ...
match anotherState with
| hello -> ()
| hello when state = Initializing -> ()
| hello when state = DoingStuff -> () <- won't compile
| hello when state = DoingStuff _-> () <- won't compile either
所以我必须在我的州里添加一个助手:
type State =
| Initializing
| DoingStuff of SubState
| DoingNothing
member this.IsDoingStuff =
match this with
| DoingStuff _ -> true
| _ -> false
然后我可以用进行我的主要比赛
match anotherState with
| hello -> ()
| hello when state = Initializing -> ()
| hello when state.IsDoingStuff -> () <- this works
但我真的很喜欢
| hello when state = DoingStuffAndIDontCareAboutTheSubState -> ()
有没有一种很好的语法方法来满足when条件并忽略"DoingStuff"的值?
我知道我可以做:
match anotherState, state with
| hello, DoingStuff _ ->
但在许多情况下,我不需要第二个值,所以我试图找到一个可以保留when语句的解决方案。
不需要使用匹配表达式。您可以在这里使用正常的标识符模式匹配:
let state anotherState =
match anotherState with
| Initializing -> ()
| DoingStuff _ -> ()
| DoingNothing ->
你也可以嵌套这些并检查子状态:
let state anotherState =
match anotherState with
| Initializing -> ()
| DoingStuff DoingA -> ()
| DoingStuff DoingB -> ()
| DoingStuff AFewMore -> ()
| DoingNothing ->
如果你想在匹配案例中使用一个表达式,匹配表达式是有用的,例如,假设你有这样的:
type Foo =
| Bar
| Baz of int
let state foo =
match foo with
| Bar -> ()
| Baz 0 -> ()
| Baz 1 -> ()
| Baz i when i < 10 -> ()
| Baz _ -> ()
您正试图将when
用于应该使用模式匹配的东西;最后一个例子是实现这一点的惯用方法:
match anotherState, state with
| hello, DoingStuff _ ->
when
适用于不能这样做的情况,并且会严重损害编译器进行穷尽性检查的能力。
这一切都是假设您在实际代码中也对anotherState
进行模式匹配,否则这不需要成为match
的一部分。