更高种类的类型作为haskell中的类型变量

时间:2019-12-23 02:31:33

标签: haskell higher-kinded-types type-variables

我上课

import Linear

class Coordinate c where
    rotate :: Num a => Quaternion a -> c a -> c a
    translate :: Num a => V3 a -> c a -> c a

,我已经为其定义了实例

instance Coordinate V3 where
    rotate _ = id
    translate p = (p+)

instance Coordinate Quaternion where
    rotate o = (o*)
    translate _ = id

现在,我想为该类的一对成员定义一个实例。

instance (Coordinate a, Coordinate b) => Coordinate (a, b) where
    rotate o (a, b) = (rotate o a, rotate o b)
    translate p (a, b) = (translate p a, translate p b)

问题在于,这不起作用,因为编译器需要ab的参数。但是添加类似

的类型约束
instance (Coordinate a, Coordinate b, Num c) => Coordinate (a c, b c) where
    move p (a, b) = (move p a, move p b)
    translate p (a, b) = (translate p a, translate p b)

也不起作用,因为这会导致表达式的类型为*而不是* -> *。我可以看到以上两种情况都不正确,但是我不确定如何解决。我想应该有某种形式的约束来使Numa的{​​{1}}类型保持相同,但是我不知道从语法上看起来会是什么样。

1 个答案:

答案 0 :(得分:7)

您不能为内置对类型创建此Coordinate类的实例。您需要更改其中之一。

  • 可以将Coordinate类更改为以普通的Type作为参数:

    {-# LANGUAGE FlexibleContexts, TypeFamilies #-}
    
    import Data.Kind (Type)
    
    class Num (Component c) => Coordinate c where
        type Component c :: Type -- every Coordinate type has a Component type
        rotate :: Quaternion (Component c) -> c -> c
        translate :: V3 (Component c) -> c -> c
    

    例如V3实例现在看起来像

    instance Num a => Coordinate (V3 a) where
        type Component (V3 a) = a
        rotate _ = id
        translate = (+)
    

    该对实例将使用等式约束,这就是您要寻找的东西

    instance (Coordinate a, Coordinate b, Component a ~ Component b) => Coordinate (a, b) where
        type Component (a, b) = Component a -- or = Component b
        rotate p (l, r) = (rotate p l, rotate p r)
        translate p (l, r) = (translate p l, translate p r)
    
  • 使用Product代替配对:

    import Data.Functor.Product
    
    instance (Coordinate a, Coordinate b) => Coordinate (Product a b) where
        rotate p (Pair l r) = Pair (rotate p l) (rotate p r)
        translate p (Pair l r) = Pair (translate p l) (translate p r)
    
相关问题