我正在学习RX,并尝试将C#中的某些代码移植到F#中。
以下是使用计时器的C#示例:

Console.WriteLine("Current Time: " + DateTime.Now);
var source = Observable.Timer(TimeSpan.FromSeconds(5), TimeSpan.FromSeconds(1)).Timestamp();
using (source.Subscribe(x => Console.WriteLine("{0}: {1}", x.Value, x.Timestamp)))
      {
       Console.WriteLine("Press any key to unsubscribe");
       Console.ReadKey();
      }
Console.WriteLine("Press any key to exit");
Console.ReadKey();


以下是我的代码尝试执行的操作:

#light
open System
open System.Collections.Generic
open System.Linq
open System.Reactive
open System.Reactive.Linq
open System.Reactive.Subjects


printfn "Current Time: %A" DateTime.Now

let source = Observable.Timer(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds(1.0)).Timestamp()
source.Subscribe(fun x -> printfn "%A %A" x.Value x.Timestamp) |> ignore


但是我遇到了编译器错误:


错误1根据此程序点之前的信息查找不确定类型的对象。在此程序指向之前可能需要类型注释,以约束对象的类型。这样可以解决查找问题。


我不知道x.Valuex.Timestamp的类型是什么。
顺便说一句,我也不知道如何在F#中使用C#进行重写。
请向我显示正确的代码。

最佳答案

下面是从C#到F#的“直接翻译”:

open System
open System.Reactive
open System.Reactive.Linq

printfn "Current Time: %A" DateTime.Now
let source = Observable.Timer(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds      (1.0)).Timestamp()
using (source.Subscribe(fun (x:Timestamped<int64>) -> printfn "%A %A" x.Value x.Timestamp))
    (fun _ ->
        printfn "Press any key to unsubscribe"
        Console.ReadKey() |> ignore
    )

printfn "Press any key to stop"
Console.ReadKey() |> ignore


运行时,允许它经过5秒钟,然后才能看到1秒计时器事件如何开始流入。

附录:lambda表达式中的输入参数的类型,而该参数又是Iobservable.Subscribe()的参数,是我们调用IObservableSubscribe()的值的类型,即构成IObservable

反过来,source表示source方法的结果,该方法返回可观察的序列,该序列在适当的时间以及每个周期之后产生一个值。此序列的类型为Observable.Timer(DateTimeOffset, TimeSpan)

当将IObservable<int64>方法应用于Timestamp()时,将产生IObservable<int64>

因此,最终我们的IObservable<Timestamped<int64>>source类型的IObservable,上面的代码片段反映为Timestamped<int64>中匿名函数的参数x的显式类型。

关于f# - 使用计时器进行F#RX,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/8771937/

10-10 19:16