注意:我可能不需要将Scalar添加到Eq中,尽管如果我能弄清楚如何做到这一点,它应该可以解决问题。
因此,我正在尝试向ForceLayout模块添加一些功能。向粒子添加质量,如下所示:
data Particle v = Particle {
_pos :: Point v
, _vel :: v
, _force :: v
, _mass :: Scalar v
}
deriving (Eq, Show)但是Scalar不在Eq或Show中!所以这不能编译。不过,质量应该是与其他矢量“兼容”的标量。我该如何协调这一点呢?我对类型族的理解不够,无法分析这种情况。我试过了,但它们很难掌握。不确定是否有必要或可能将Scalar添加到Eq。
发布于 2012-06-08 01:34:21
如果想要显示mass字段,show实例必须如下所示
instance (Show v, Show (Point v), Show (Scalar v)) => Show (Particle v) where可以说,GHC不能解决这个问题是一个bug,或者至少是一个缺失的特性。幸运的是,通过一些扩展繁重的工作,我们可以自己给它提供上下文:
{-# LANGUAGE StandaloneDeriving, TypeFamilies,
FlexibleContexts, UndecidableInstances #-}
{- ... -}
deriving instance (Show v, Show (Point v), Show (Scalar v)) => Show (Particle v)这是一个在the GHC user guide中描述的“独立的派生声明”,它在这里的目的基本上是为了让我们可以指定一个GHC通常无法解决的上下文。
这应该能起到作用。我有点担心UndecidableInstances,因为它看起来确实应该可以定义Point和Scalar的实例,使该实例是循环的,但尽管我尽了最大努力,我仍然无法使类型检查器循环,所以它可能是好的。
https://stackoverflow.com/questions/10935985
复制相似问题