【问题标题】:Pattern match a polymorphic type in a concrete type in Elm模式匹配 Elm 中具体类型中的多态类型
【发布时间】:2017-01-01 13:35:14
【问题描述】:

我正在使用 elm-form:https://github.com/etaque/elm-form/,我需要将多态类型模式匹配为具体类型,但出现下一个错误:

The pattern matches things of type:

    TranslationId

But the values it will actually be trying to match are:

    e

Hint: Your type annotation uses type variable `e` which means any type of value
can flow through. Your code is saying it CANNOT be anything though! Maybe change
your type annotation to be more specific? Maybe the code has a problem? More at:
<https://github.com/elm-lang/elm-compiler/blob/0.18.0/hints/type-annotations.md>

有问题的代码是这样的:

translateError : ErrorValue e -> String
translateError error =
    case error of
        InvalidEmail ->
            translate English ErrInvalidEmail

        Empty ->
            translate English ErrEmpty

        CustomError PasswordNotMatch ->
            translate English PasswordNotMatch

        x ->
            toString x

错误值类型https://github.com/etaque/elm-form/blob/f9480cb8646ebc9f78f13d3a7482c463c5275776/src/Form/Error.elm#L19:

type ErrorValue e
    = Empty
    | InvalidString
    | InvalidEmail
    | InvalidUrl
    | InvalidFormat
    | InvalidInt
    | InvalidFloat
    | InvalidBool
    | InvalidDate
    | SmallerIntThan Int
    | GreaterIntThan Int
    | SmallerFloatThan Float
    | GreaterFloatThan Float
    | ShorterStringThan Int
    | LongerStringThan Int
    | NotIncludedIn
    | CustomError e

TranslationId 类型https://github.com/werner/madison-elm/blob/master/src/elm/Translations/Utils.elm#L9

type TranslationId
    = ErrInvalidEmail
    | PasswordNotMatch
    | ErrEmpty

我想出了一个解决方案,但它看起来很奇怪,我不确定它是否正确https://github.com/werner/madison-elm/blob/master/src/elm/Translations/FormErrors.elm#L7

translateError : ErrorValue e -> String
translateError error =
    case error of
        InvalidEmail ->
            translate English ErrInvalidEmail

        Empty ->
            translate English ErrEmpty

        CustomError e ->
            case (toString e) of
                "PasswordNotMatch" ->
                    translate English PasswordNotMatch
                x ->
                    toString x

        x ->
            toString x

【问题讨论】:

  • 那是因为您没有指定 etranslateError : ErrorValue e -&gt; String 中的内容 - 所以它对此一无所知。也许传入e -&gt; String 函数?

标签: elm


【解决方案1】:

正如@reactormonk 所说,您没有在类型定义中处理类型变量。 elm-form 通过此类型变量为自定义错误提供了灵活性,如果您想使用自定义错误,您必须自己提供(如果您不这样做,那么您可以在整个代码中使用该变量没有问题)。

特别是 ErrorValue 有一个类型变量 e 您需要指定:在不使用 CustomError 构造函数的代码中无关紧要,但在 translateError 中很重要,因为您正在尝试模式匹配在自定义错误上。看起来你想要的类型是TranslationId 所以你想要

translateError : ErrorValue TranslationId -> String
translateError error =
    case error of
        InvalidEmail ->
            translate English ErrInvalidEmail

        Empty ->
            translate English ErrEmpty

        CustomError PasswordNotMatch ->
            translate English PasswordNotMatch

        x ->
            toString x

【讨论】:

  • 我这样做了,然后我从here 调用它,然后我将类型签名更改为:errorFor : FieldState TranslationId String -&gt; Html msg,然后我从here 收到错误,最后我卡住了。跨度>
  • 我试着让我的答案更完整一点,但建议是一样的
  • 是的,非常感谢您抽出宝贵时间检查了这一点。但是,也许我解释得不够充分,按照您的建议,我得到了这个 point,它从 elm-form 包中调用了一个函数 getFieldAsString,如您所见 here,它需要一种形式: FieldState e String,但是我通过了:FieldState TranslationId String,这会产生错误。
  • 我可以分叉包并更改 getFieldAsString 的类型签名,但我在想也许有更好的解决方案,谢谢大家的帮助。
  • 您得到的错误在您的代码中,而不是在 elm-form 中。您的错误是 github.com/werner/madison-elm/blob/master/src/elm/Translations/… 并且是因为您尝试在类型 CustomError e 上进行模式匹配而没有指定 e 是什么类型
猜你喜欢
  • 1970-01-01
  • 2019-06-28
  • 2013-03-17
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-12-01
相关资源
最近更新 更多