像OCaml一样的Haskell私人记录

Cal*_*mer 4 haskell record

在OCaml模块签名中,我可以写:

type monotype = private {
  monotype_free_variables: StringSet.t Lazy.t;
  monotype_description: monotype_description;
}
Run Code Online (Sandbox Code Playgroud)

(注意使用private.)

这允许导入我的模块的代码模式匹配字段,monotype_description但不允许代码导入我的模块来构造记录.

我可以在Haskell中编写具有类似访问权限的代码吗?我想monotypeDescription在不允许记录构造的情况下对场进行模式匹配.

我知道PatternSynonyms存在语言扩展,但我不知道如何使用它.如果可以的话,我也更喜欢更简单的解决方案.

Ale*_*lec 7

您不能在不允许至少记录更新的情况下匹配字段(您是否导入字段).我认为限制更多是因为没有明显的语法只导入访问者...

真正的解决方案是使用PatternSynonyms.你需要一个单向模式:

{-# LANGUAGE PatternSynonyms #-}
module MyModule ( Monotype(Monotype) ) where

import Data.Set

data Monotype = MT (Set String) String

pattern Monotype :: Set String -> String -> Monotype
pattern Monotype { monotype_free_variables, monotype_description }
  <- MT monotype_free_variables monotype_description
Run Code Online (Sandbox Code Playgroud)

现在,您可以匹配Monotype { monotype_free_variables, monotype_description }但不能构建它:

?> Monotype { monotype_free_variables = f1, monotype_description = f2 } = m1
?> Monotype f1 f2 = m1
?> m3 = Monotype { monotype_free_variables = mempty, monotype_description = "" }
<interactive>:3:6: error:
    • non-bidirectional pattern synonym ‘Monotype’ used in an expression
    • In the expression:
        Monotype
          {monotype_free_variables = mempty, monotype_description = ""}
      In an equation for ‘m3’:
          m3
            = Monotype
                {monotype_free_variables = mempty, monotype_description = ""}
?> m3 = Monotype mempty ""

<interactive>:4:6: error:
    • non-bidirectional pattern synonym ‘Monotype’ used in an expression
    • In the expression: Monotype mempty ""
      In an equation for ‘m3’: m3 = Monotype mempty ""
Run Code Online (Sandbox Code Playgroud)

  • 哇,我从未想过导出一个字段会允许记录更新.让人惊讶. (3认同)