繁体   English   中英

Haskell:带有“newtype”的“多个”参数

[英]Haskell: “multiple” parameters with `newtype`

免责声明:我对 Haskell 很陌生

我正在尝试基于设计在 haskell 中构建一个不透明的多态队列 ADT:

module Queue (Queue, empty, isEmpty, frontOf, enqueue, dequeue) where

data Queue a = Queue [a] [a] deriving Show

enqueue :: Queue a -> a -> Queue a
enqueue (Queue xs ys) y     = Queue xs (y:ys)

dequeue :: Queue a -> Maybe (Queue a)
dequeue (Queue [] [])       = Nothing
dequeue (Queue [] ys)       = dequeue (Queue (reverse ys) [])
dequeue (Queue (x:xs) ys)   = Just (Queue xs ys)

但我正在尝试使用newtype使其真正不透明:

module Queue (Queue, empty, isEmpty, frontOf, enqueue, dequeue) where

enqueue :: Queue a -> a -> Queue a
dequeue :: Queue a -> Maybe (Queue a)

newtype Queue a = Qimp ???

...function implementations

所以我的问题是,我用什么来代替??? .

我试过这个:

newtype Queue a = Qimp ([] [])

但这似乎打破了我函数中的逻辑,原因对于训练有素的眼睛来说可能是显而易见的(但对我来说并不明显)。

我似乎陷入了困境,因为我的原始实现使用了两个列表来有效地实现一个队列,但是newtype在构造函数中只需要一个参数。 在使用newtype是否有一种通用/标准的方法来模拟多个构造函数参数?

这个问题似乎是 XY 问题的一个案例,因此我将尝试解决实际问题并回答您提出的问题。

当我使用一个带有两个列表的构造函数定义data类型时,用户是否可以将其视为列表元组?

不可以。 data定义创建自己独特的类型(不像type定义,它只创建一个别名)。

关于不透明性, data是否还有其他问题?

如果导出数据类型的构造函数,用户可以通过模式匹配使用它们来获取构成队列的列表。 为了防止这种情况,您不应该导出您的构造函数。

什么是之间的区别newtypedata类型?

newtype基本上是一个的受限版本data ,可以更有效地编译类型。 限制是它只能有一个构造函数,并且那个构造函数只能有一个参数。

有关于懒惰和未结束(数据类型可以包含底部,一个NEWTYPE只能是底部)两者之间的语义差别,但在大多数情况下这并不重要,人们只需使用newtype每当限制得到满足获得更好的性能。

使用newtype会使类型更不透明吗?

不, newtype的行为与data类型完全相同(以上面提到的懒惰差异为模)。 我所说的关于data类型的不透明性的同样的事情也适用于newtype

一个可以newtype有多个参数?

不,但它可以有一个元组参数。 你可以这样定义它:

data Queue a = Queue ([a], [a]) deriving Show

然而,人们几乎没有理由这样做。 data类型上使用newtype的原因是性能:您希望保护一级间接。 然而,使用元组只会重新引入您刚刚保存的间接,因此它最终完全相同,性能明智。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM