我有一个使用记录语法的Haskell类型。
data Foo a = Foo { getDims :: (Int, Int), getData :: [a] }
我不想导出Foo
值构造函数,这样用户就无法构建无效的对象。但是,我想导出getDims
,以便用户可以获取数据结构的维度。如果我这样做
module Data.ModuleName(Foo(getDims)) where
用户可以使用getDims
来获取尺寸,但问题在于他们也可以使用记录更新语法来更新字段。
getDims foo -- This is allowed (as intended)
foo { getDims = (999, 999) } -- But this is also allowed (not intended)
我希望避免后一种情况,因为这将使数据处于无效状态。我意识到可以简单地不使用记录。
data Foo a = Foo { getDims_ :: (Int, Int), getData :: [a] }
getDims :: Foo a -> (Int, Int)
getDims = getDims_
但这似乎是绕过问题的一种比较迂回的方式。有没有一种方法可以在仅导出记录名称以进行读取访问而不进行写入访问的情况下继续使用记录语法?