无法在计算表达式中编译代码,在 F# 中

can't compile code in computation expression, in F#

我有这个功能:

let rec retryAsync<'a> (shouldRetry: 'a -> bool) (retryIntervals: TimeSpan list) (onRetryNotice: int -> unit) (request: unit -> Async<'a>) : Async<'a> =
    async {
        let! result = request()
        match shouldRetry result, retryIntervals with
        | true, head::rest ->
            onRetryNotice retryIntervals.Length
            Thread.Sleep(head)
            return! retryAsync shouldRetry rest onRetryNotice request
        | false, _
        | _, [] ->
            return result
    }

我在这样的 asyncResult 块中使用它:

asyncResult {
    let! x = Retry.retryAsync
                 Retry.shouldRetryExchange
                 Retry.defaultRetryIntervals
                 (fun r -> warn $"retry {r}/{Retry.defaultRetryIntervals.Length}")
                 (fun _ -> loadExchangeSettingsAsync rest)
    ...
    return ...
}

但在某些情况下,我想忽略结果;然而:

asyncResult {
    do!  Retry.retryAsync
             Retry.shouldRetryExchange
             Retry.defaultRetryIntervals
             (fun r -> warn $"retry {r}/{Retry.defaultRetryIntervals.Length}")
             (fun _ -> loadExchangeSettingsAsync rest)
    ...
    return ...
}

会给我:

[FS0001] This expression was expected to have type 'Result<unit,ExchangeError>' but here has type 'unit'

我不明白为什么因为表达式返回正确的类型,它与上面的相同。

do! 仅适用于 return Async<unit> 的表达式,因此您必须先将其通过管道传输到 Async.Ignore

do!  Retry.retryAsync
             Retry.shouldRetryExchange
             Retry.defaultRetryIntervals
             (fun r -> warn $"retry {r}/{Retry.defaultRetryIntervals.Length}")
             (fun _ -> loadExchangeSettingsAsync rest)
     |> Async.Ignore