我从XmlProvider中获得了巨大的价值,因为当我加载XML或XSD时,它提供了大量的类型定义。但是,请考虑以下XML:
<period>
<start>01/01/2018</start>
<end>02/02/2018</end>
</period>
我可以谈谈类型提供者给我一个受约束的数据类型,以使“ end”不能在“ start”之前。还是在XmlProvider进行繁重的工作之后施加一些约束?
答案 0 :(得分:2)
在这种情况下,我会将其视为边缘情况,并认为它是“未验证的模型”。因此,通常在F#中,我们将使用验证功能将未经验证的模型转换为经过验证的模型。 (我通常为此使用Result<'T, 'E>
。)
let validateXmlDates xml =
if xml.period.start > xml.period.end then
Error "Period start must be before period end"
else Ok xml
现在,您所做的任何事情都应该期望Result<XmlType, string>
,它将使您能够通过并保证它符合您的要求。您也可以使用Result.bind
链接验证 1 :
Ok xml
|> Result.bind (validateXmlDates)
|> Result.bind (validateXml...)
|> Result.bind (validateXml...)
一些相关的读物:Railway Oriented Programming (F# for Fun and Profit)
获得结果后,可以使用简单的match
来触发下一步:
match validatedXml with
| Ok xml -> ...
| Error str -> ...
然后,您将在Ok
分支中执行下一个逻辑步骤,并处理Error
分支中的错误。
1:Result.bind (fn)
实际上是以下内容的简写:
match result with
| Error e -> Error e
| Ok v -> fn v