Haskell:Typeclass意味着其他Typeclass
在Haskell中有可能让一个typeclass暗示另一个typeclass吗?例如,假设有一堆“东西”可以按“属性”排序: 由于多种原因,这显然不起作用。我想知道这是否可能?您可以这样做:Haskell:Typeclass意味着其他Typeclass,haskell,Haskell,在Haskell中有可能让一个typeclass暗示另一个typeclass吗?例如,假设有一堆“东西”可以按“属性”排序: 由于多种原因,这显然不起作用。我想知道这是否可能?您可以这样做: instance Ord Person where compare p1 p2 = compare (age p1) (age p2) 现在,标准的正如您所指定的那样,OrdByKey类只能有一个实例 每种类型,当听起来您希望能够声明实例时 对于记录类型中的每个字段 要实现这一点,您必须将字段类型
instance Ord Person where
compare p1 p2 = compare (age p1) (age p2)
现在,标准的
正如您所指定的那样,OrdByKey
类只能有一个实例
每种类型,当听起来您希望能够声明实例时
对于记录类型中的每个字段
要实现这一点,您必须将字段类型放入类中
定义也一样。这使您可以执行以下操作:
{-# LANGUAGE MultiParamTypeClasses #-}
data Person = Person { name :: String, age :: Int }
class (Ord r) => OrdByKey o r where
orderKey :: o -> r
instance OrdByKey Person Int where
orderKey p = age p
x <=? y = (orderKey x :: Int) <= (orderKey y :: Int)
您将无法在名称
和
ssn
字段。您可以通过将每个字段包装成一个
newtype
因此每个字段都有一个唯一的类型。所以你的人
类型看起来
像
这将导致大量的newtype
浮动
这样做的真正缺点是需要为
orderKey
函数。我建议使用
Data.Function
编写适当的比较函数。我想
函数式
compareByKey :: (Ord b) => (a -> b) -> a -> a -> Bool
compareByKey = on (<=)
compareByKey::(Ord b)=>(a->b)->a->a->Bool
compareByKey=on(如果您的目标只是根据记录中的特定字段排序,那么您可以为Person
定义Ord
的实例来比较该特定字段。@sabauma是的,但我正在寻找“可以通过某个键进行比较”的泛化对于这个特殊的例子,看看函数:comparing age you me
作为一个更通用的操作符,然后可以看看comparing
。它的类型是(b->b->c)->(a->b)->a->a->c
,所以comparing age=on comparing age
,但是你也可以在(=)上设置f
在应用f
后测试两件事情是否相等。看起来使用多参数类型类是一种干净的方法。谢谢!
instance Ord Person where
compare p1 p2 = compare (age p1) (age p2)
{-# LANGUAGE MultiParamTypeClasses #-}
data Person = Person { name :: String, age :: Int }
class (Ord r) => OrdByKey o r where
orderKey :: o -> r
instance OrdByKey Person Int where
orderKey p = age p
x <=? y = (orderKey x :: Int) <= (orderKey y :: Int)
data Person = Person { name :: String, age :: Int, ssn :: String}
data Person = Person { name :: Name, age :: Age, ssn :: SSN}
compareByKey :: (Ord b) => (a -> b) -> a -> a -> Bool
compareByKey = on (<=)