F# 忽略模式匹配中的模式
F# Ignore a pattern in pattern match
我可能以错误的方式思考这个问题,但我想忽略 Some
案例以外的任何案例。这是我正在使用的一些示例代码 | _ -> ignore
但这似乎是错误的。有没有更好或更惯用的方法来做到这一点?我正在将一些 OOP C# 代码转换为 F#,可能会出现错误。
match solarSystem.MinerCoords |> Map.tryFind minerId with
| Some currentMinerCoords ->
match solarSystem.Minables |> Map.tryFind currentMinerCoords with
| Some _ ->
do! GetMinerActor(minerId).StopMining() |> Async.AwaitTask
| _ -> ignore
| _ -> ignore
您似乎在 async
计算表达式中 returns Async<unit>
。所以你应该用 return ()
替换 ignore
(其中 ()
是单位值)以便所有分支 return 相同的类型:
match solarSystem.MinerCoords |> Map.tryFind minerId with
| Some currentMinerCoords ->
match solarSystem.Minables |> Map.tryFind currentMinerCoords with
| Some _ ->
do! GetMinerActor(minerId).StopMining() |> Async.AwaitTask
| _ -> return ()
| _ -> return ()
编辑:显示整个异步块的简化版本,以及如何继续 运行 之后的更多代码:
async {
match Some 1 with
| Some a ->
printfn "Maybe do this"
do! Async.Sleep 500
| _ -> ()
printfn "Always do this"
do! Async.Sleep 500
printfn "Finished" }
你可以让每个分支产生一个异步,然后你就可以执行它了。像这样:
let dummyAsync = async { return () }
let theAsync =
match solarSystem.MinerCoords |> Map.tryFind minerId with
| Some currentMinerCoords when solarSystem.Minables |> Map.tryFind currentMinerCoords |> Option.isSome ->
GetMinerActor(minerId).StopMining() |> Async.AwaitTask
| _ ->
dummyAsync
do! theAsync
注意使用 when
关键字删除一个不必要的分支。
更习惯地说,当您以嵌套方式匹配多个选项值时,您应该使用函数 Option.bind
and/or Option.map
:
let dummyAsync = async { return () }
let theAsync =
solarSystem.MinerCoords
|> Map.tryFind minerId
|> Option.bind (fun currentMinerCoords -> solarSystem.Minables |> Map.tryFind currentMinerCoords)
|> Option.map (fun _ -> GetMinerActor(minerId).StopMining() |> Async.AwaitTask)
|> Option.defaultValue dummyAsync
do! theAsync
我可能以错误的方式思考这个问题,但我想忽略 Some
案例以外的任何案例。这是我正在使用的一些示例代码 | _ -> ignore
但这似乎是错误的。有没有更好或更惯用的方法来做到这一点?我正在将一些 OOP C# 代码转换为 F#,可能会出现错误。
match solarSystem.MinerCoords |> Map.tryFind minerId with
| Some currentMinerCoords ->
match solarSystem.Minables |> Map.tryFind currentMinerCoords with
| Some _ ->
do! GetMinerActor(minerId).StopMining() |> Async.AwaitTask
| _ -> ignore
| _ -> ignore
您似乎在 async
计算表达式中 returns Async<unit>
。所以你应该用 return ()
替换 ignore
(其中 ()
是单位值)以便所有分支 return 相同的类型:
match solarSystem.MinerCoords |> Map.tryFind minerId with
| Some currentMinerCoords ->
match solarSystem.Minables |> Map.tryFind currentMinerCoords with
| Some _ ->
do! GetMinerActor(minerId).StopMining() |> Async.AwaitTask
| _ -> return ()
| _ -> return ()
编辑:显示整个异步块的简化版本,以及如何继续 运行 之后的更多代码:
async {
match Some 1 with
| Some a ->
printfn "Maybe do this"
do! Async.Sleep 500
| _ -> ()
printfn "Always do this"
do! Async.Sleep 500
printfn "Finished" }
你可以让每个分支产生一个异步,然后你就可以执行它了。像这样:
let dummyAsync = async { return () }
let theAsync =
match solarSystem.MinerCoords |> Map.tryFind minerId with
| Some currentMinerCoords when solarSystem.Minables |> Map.tryFind currentMinerCoords |> Option.isSome ->
GetMinerActor(minerId).StopMining() |> Async.AwaitTask
| _ ->
dummyAsync
do! theAsync
注意使用 when
关键字删除一个不必要的分支。
更习惯地说,当您以嵌套方式匹配多个选项值时,您应该使用函数 Option.bind
and/or Option.map
:
let dummyAsync = async { return () }
let theAsync =
solarSystem.MinerCoords
|> Map.tryFind minerId
|> Option.bind (fun currentMinerCoords -> solarSystem.Minables |> Map.tryFind currentMinerCoords)
|> Option.map (fun _ -> GetMinerActor(minerId).StopMining() |> Async.AwaitTask)
|> Option.defaultValue dummyAsync
do! theAsync