我有一个 Haskell 函数,它接受用户输入,还有另一个函数验证此输入。当然,验证可能会失败,在这种情况下,我想返回一条错误消息,提供有关错误操作的一些反馈。
我知道有很多方法可以做到这一点。根据我的一点经验,似乎最好的方法是使用Either String a
。让我失望的是我不关心a
。要么失败并且我想存储更多信息,要么成功。这a
被浪费了。
正在使用Maybe String
存储错误消息的可接受的方式?对我来说这感觉是倒退的,但完全忽略了右边的价值Either
感觉也很不好。这里什么是规范的?
我鼓励使用Except String ()
(or Either String ()
) over Maybe String
,出于以下几个原因:
- 稍后您可能会发现验证函数返回数据结构的某些部分很方便。例如,在验证
String
是电话号码,您可能想要返回区号、号码的第一部分和第二部分,给出如下验证类型String -> Except String (Int, Int, Int)
或类似的。使不返回任何有趣内容的验证器具有类型Foo -> Except String ()
使它们只是这种模式的一个特例——因此更容易组合在一起。
-
继续“组合在一起”部分,您稍后可能会发现您想要用较小的验证器构建一个大型验证器。也许您有一个验证器来检查一个人是否指定了有效的年龄和出生日期,并且希望以此构建一个验证器来检查年龄是否与出生日期相符。这Monad
实例为Either
会在这里提供帮助;例如:
validatePerson p now = do
age <- validateAge p
date <- validateBirthdate p
validateMatchingAgeAndDate age date now
或者也许有两种方法可以正确验证某些值,而您希望允许其中一种。然后bigValidator v = option1 v <|> option2 v
是一种结合两种验证方式的廉价而愉快的方式。
附带的好处是,这些结合现有验证器来创建更大验证器的方法将立即被其他 Haskellers 所识别。
有一个非常强烈的约定Nothing
是一个失败。使用相反的约定并不是problem,这是必然的,但可能会让其他贡献者感到困惑,也可能在不久的将来让你自己感到困惑。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)