如何在 F# 中创建 C# 样式的异步成员?

How do I create a C# style async member in F#?

在 C# 中,您可以像这样用 async 注释方法:

class Foo
{
    public async void Bar()  
    {  

    }  
}

这与 F# 不同 async;我相信在 F# 中,这些被称为 tasks.

那么,如何在 F# 中编写 C# 风格的 async 成员函数?

// Not real code
type Foo () = 
  member async this.Bar () = 
    ()

解决方案必须编译为具有与上述 C# 相同的 public 接口的 IL。

Async.StartAsTask 应该这样做。这会给你 Threading.Tasks.Task<'a>

let bar  =
    async{
        
        return ()
    }
    |>Async.StartAsTask

C# async 方法只是一个返回类型 Task<T> 值的方法。 C# 编译器使用 async 关键字来确定允许您在代码块内使用 await,但据我所知,它在编译代码中没有以任何方式表示。

您说“解决方案必须编译为相同的 IL”- 这不容易实现,因为 F# 以不同方式实现异步操作。但是,您可以使用如下方式将其编译为具有相同 public 接口的 IL:

type Foo () = 
  member this.Bar () = Async.StartAsTask <| async {
    // yadda yadda 
    }

异步操作是使用标准 F# 异步工作流实现的,因此在表面上,这创建了一个 F# Async<T>,但 Async.StartAsTask 操作将其转换为 Task<T> 类型,这是 C# 所期望的。

编辑: 另一种选择是使用 TaskBuilder computation expression,它允许您使用类似这样的东西直接创建 .NET 任务:

type Foo () = 
  member this.Bar () = task {
    // yadda yadda 
    }