我正在使用F#中的异步工作流和代理工作很多,而我对事件的深入了解我注意到Event <_>()类型不是线程安全的.在这里,我不是在谈论举办活动的常见问题.我实际上是在谈论订阅和删除/处理事件.出于测试目的,我写了这个简短的程序
let event = Event<int>()
let sub = event.Publish
[<EntryPoint>]
let main argv =
let subscribe sub x = async {
let mutable disposables = []
for i=0 to x do
let dis = Observable.subscribe (fun x -> printf "%d" x) sub
disposables <- dis :: disposables
for dis in disposables do
dis.Dispose()
}
Async.RunSynchronously(async{
let! x = Async.StartChild (subscribe sub 1000)
let! y = Async.StartChild (subscribe sub 1000)
do! x
do! y
event.Trigger 1
do! Async.Sleep 2000
}) …Run Code Online (Sandbox Code Playgroud) 目前我正在游戏中使用Event/Observables,我遇到的一件事是消除一些冗余代码,我没有找到办法.为了解释它,我们假设我们跟随DU和这个DU的Observable.
type Health =
| Healed
| Damaged
| Died
| Revived
let health = Event<Health>()
let pub = health.Publish
Run Code Online (Sandbox Code Playgroud)
我有很多这种结构.将所有"健康"消息组合在一起是有帮助的,并且在某些情况下需要,但在某些情况下我只关心特殊的消息.因为仍然经常需要我Observable.choose用来分隔这些信息.我有这样的代码.
let healed = pub |> Observable.choose (function
| Healed -> Some ()
| _ -> None
)
let damaged = pub |> Observable.choose (function
| Damaged -> Some ()
| _ -> None
)
Run Code Online (Sandbox Code Playgroud)
编写这种代码实际上是非常重复和烦人的.我有很多这些类型和消息.因此,函数式编程的一个"规则"是"参数化所有事物".所以我写了一个函数only来帮助我.
let only msg pub = pub |> Observable.choose (function
| x when x = msg -> Some ()
| _ …Run Code Online (Sandbox Code Playgroud)