定义区分联合的默认值

Ren*_*rer 4 f# discriminated-union

我想为一个有区别的联合定义一个默认值,如下所示:

open System.Linq

type Result =
| Ok
| Error

let results : seq<Result> = [] |> Seq.ofList

let firstResult = results.FirstOrDefault()
// I want firstResult to be Error, currently it is null.
Run Code Online (Sandbox Code Playgroud)

选项<'a>以这种方式工作(firstResult将是None),所以它应该是可能的.谢谢你的帮助.

编辑:我正在使用SQLDataProvider,并希望编写类似的代码

let userEmail =
    query {
        for user in dbContext.Public.Users do
        where (user.Id = 42)
        select (Ok user.Email)
        headOrDefault
        // should result in Error
        // when no user with Id=42 exists 
    }
Run Code Online (Sandbox Code Playgroud)

我的实际结果类型如下所示:

type Result<'a> =
| Ok of 'a
| Failure of string // Expected, e. g. trying to log in with a wrong password
| Error // Unexpected
Run Code Online (Sandbox Code Playgroud)

返回选项时,调用者将无法区分失败和错误.

The*_*Fox 7

通常,F#避免使用默认值的概念,而是使所有内容尽可能明确.返回一个选项并让调用者决定特定用例的默认值是更惯用的.

FirstOrDefault方法只能返回任何类型的.NET默认值.因此对于它将返回的任何类null,对于数字,它将返回零.

我会推荐这种方法,而不是假设你想要的默认值是Ok:

results |> Seq.tryHead |> Option.defaultValue Ok
Run Code Online (Sandbox Code Playgroud)

  • 我认为这里所需的值是"错误".但我完全同意这个答案! (2认同)