2012-12-04 53 views
6

好吧,我正试图围绕typeclasses打包头,所以我试图为几何向量操作定义一个typeclass。我设法让它在组件方面工作+,-,*,/;,但我正在努力与点产品。Haskell向量类型:函数[a] - > [a] - > a

class GeomVector a where 
    (>+) :: a -> a -> a 
    (>-) :: a -> a -> a 
    (>*) :: a -> a -> a 
    (>/) :: a -> a -> a 

    (>.) :: a -> a -> Double 

data Vector a = Vec [a] 
       deriving Show 

instance (Fractional a) => GeomVector (Vector a) where 
    (>+) (Vec u) (Vec v) = Vec $ zipWith (+) u v 
    (>-) (Vec u) (Vec v) = Vec $ zipWith (-) u v 
    (>*) (Vec u) (Vec v) = Vec $ zipWith (*) u v 
    (>/) (Vec u) (Vec v) = Vec $ zipWith (/) u v 

    (>.) (Vec u) (Vec v) = sum $ u >* v 

显然我的(>)将无法工作,因为结果是一个类型Fractional a,不Double的实例定义。

但我不知道如何从类的声明中得到这种行为。

我倒是喜欢做的是:

class GeomVector [a] where 
    (>.) :: [a] -> [a] -> a 

但这是无效的,因为[a]是一个类型,而不是一个类型变量。

我希望我可以更好地解释这一点,但我老实说不够了解。希望代码能够让我更加明白我正在努力挣扎的东西。

+1

我想你需要另一个类型变量来表示标量的类型,即'class GeomVector a s where ...(>。):: a - > a - > s'。 – ErikR

+2

你想要的是[关联类型同义词](http://www.haskell.org/haskellwiki/GHC/Type_families#An_associated_type_synonym_example) – Lambdageek

+0

您的类声明不仅因为(>。)结果类型而存在缺陷。 您试图生成''''u'''和''v'''的点积,它们是 列表,而不是您班级的实例。 –

回答

5

这里有一个选项可以工作:

class GeomVector v where 
    (>+) :: Num a=> v a -> v a -> v a 
    (>-) :: Num a=> v a -> v a -> v a 
    (>*) :: Num a=> v a -> v a -> v a 
    (>/) :: Fractional a=> v a -> v a -> v a 
    (>.) :: Num a=> v a -> v a -> a 

data Vector a = Vec { vecList :: [a] } 
       deriving Show 

instance GeomVector Vector where 
    (>+) (Vec u) (Vec v) = Vec $ zipWith (+) u v 
    (>-) (Vec u) (Vec v) = Vec $ zipWith (-) u v 
    (>*) (Vec u) (Vec v) = Vec $ zipWith (*) u v 
    (>/) (Vec u) (Vec v) = Vec $ zipWith (/) u v 

    (>.) u v = sum $ vecList (u >* v) 

所以所有的GeomVector情况下都会有一种* -> *Monad类。而且这些方法的类型并不是不必要地限制为Fractional类型,只是因为你在那里划分了某个地方。

你也可以考虑让你的类尽可能小(使得>.是类之外的多态函数),以及你真正想要的是一个类型类。但所有这一切取决于你的设计,而且我不想假设我比你更了解这件事!

+0

可能无法将'> .'移出类,因为它需要了解每个GeomVector实例的内部结构才能完成总和。 – huon

+1

这个问题可以通过添加一个'toList'来解决。 –

+0

对不起。因此,如果有意义的话,一种选择是使类“class(Foldable v)=> GeomVector v”。 – jberryman

相关问题