packages feed

vector-space 0.3.1 → 0.4

raw patch · 9 files changed

+424/−126 lines, 9 filesPVP ok

version bump matches the API change (PVP)

API changes (from Hackage documentation)

- Data.AdditiveGroup: instance (AdditiveGroup v) => AdditiveGroup (u -> v)
- Data.Maclaurin: (**^) :: (HasBasis a s, HasTrie (Basis a), VectorSpace c s, VectorSpace s s) => (a :> s) -> (a :> c) -> (a :> c)
- Data.Maclaurin: (<*.>) :: (HasBasis a s, HasTrie (Basis a), InnerSpace b s, VectorSpace s s) => (a :> b) -> (a :> b) -> (a :> s)
- Data.Maclaurin: instance (InnerSpace u s, InnerSpace s s', VectorSpace s s, HasBasis a s, HasTrie (Basis a)) => InnerSpace (a :> u) (a :> s)
- Data.VectorSpace: instance (HasTrie u, VectorSpace v s, AdditiveGroup (u :->: v)) => VectorSpace (u :->: v) s
+ Data.ABasis: basisValue :: (HasBasis v) => Basis v -> v
+ Data.ABasis: class (VectorSpace v) => HasBasis v where { type family Basis v :: *; }
+ Data.ABasis: decompose :: (HasBasis v) => v -> [(Basis v, Scalar v)]
+ Data.ABasis: decompose' :: (HasBasis v) => v -> (Basis v -> Scalar v)
+ Data.ABasis: instance (Eq a, HasBasis u) => HasBasis (a -> u)
+ Data.ABasis: instance (s ~ Scalar u, s ~ Scalar v, HasBasis u, HasBasis v) => HasBasis (u, v)
+ Data.ABasis: instance (s ~ Scalar u, s ~ Scalar v, s ~ Scalar w, HasBasis u, HasBasis v, HasBasis w) => HasBasis (u, v, w)
+ Data.ABasis: instance HasBasis Double
+ Data.ABasis: instance HasBasis Float
+ Data.ABasis: linearCombo :: (VectorSpace v) => [(v, Scalar v)] -> v
+ Data.ABasis: recompose :: (HasBasis v) => [(Basis v, Scalar v)] -> v
+ Data.ALinearMap: lapply :: (VectorSpace u, VectorSpace v, (Scalar u) ~ (Scalar v), HasBasis u, HasTrie (Basis u)) => (u :-* v) -> (u -> v)
+ Data.ALinearMap: linear :: (VectorSpace u, VectorSpace v, HasBasis u, HasTrie (Basis u)) => (u -> v) -> (u :-* v)
+ Data.ALinearMap: type :-* u v = Basis u :->: v
+ Data.AVectorSpace: (*^) :: (VectorSpace v) => Scalar v -> v -> v
+ Data.AVectorSpace: (<.>) :: (InnerSpace v) => v -> v -> Scalar v
+ Data.AVectorSpace: (^*) :: (VectorSpace v, s ~ (Scalar v)) => v -> s -> v
+ Data.AVectorSpace: (^/) :: (VectorSpace v, s ~ (Scalar v), Fractional s) => v -> s -> v
+ Data.AVectorSpace: class (VectorSpace v) => InnerSpace v
+ Data.AVectorSpace: class (AdditiveGroup v) => VectorSpace v where { type family Scalar v :: *; }
+ Data.AVectorSpace: instance (HasTrie a, VectorSpace v) => VectorSpace (a :->: v)
+ Data.AVectorSpace: instance (RealFloat v, VectorSpace v) => VectorSpace (Complex v)
+ Data.AVectorSpace: instance (VectorSpace v) => VectorSpace (a -> v)
+ Data.AVectorSpace: instance (s ~ Scalar u, s ~ Scalar v, InnerSpace u, InnerSpace v, AdditiveGroup (Scalar v)) => InnerSpace (u, v)
+ Data.AVectorSpace: instance (s ~ Scalar u, s ~ Scalar v, VectorSpace u, VectorSpace v) => VectorSpace (u, v)
+ Data.AVectorSpace: instance (s ~ Scalar u, s ~ Scalar v, s ~ Scalar w, InnerSpace u, InnerSpace v, InnerSpace w, AdditiveGroup s) => InnerSpace (u, v, w)
+ Data.AVectorSpace: instance (s ~ Scalar u, s ~ Scalar v, s ~ Scalar w, VectorSpace u, VectorSpace v, VectorSpace w) => VectorSpace (u, v, w)
+ Data.AVectorSpace: instance (s ~ Scalar v, RealFloat v, InnerSpace v, AdditiveGroup s) => InnerSpace (Complex v)
+ Data.AVectorSpace: instance InnerSpace Double
+ Data.AVectorSpace: instance InnerSpace Float
+ Data.AVectorSpace: instance VectorSpace Double
+ Data.AVectorSpace: instance VectorSpace Float
+ Data.AVectorSpace: lerp :: (VectorSpace v, s ~ (Scalar v), Num s) => v -> v -> s -> v
+ Data.AVectorSpace: magnitude :: (InnerSpace v, s ~ (Scalar v), Floating s) => v -> s
+ Data.AVectorSpace: magnitudeSq :: (InnerSpace v, s ~ (Scalar v)) => v -> s
+ Data.AVectorSpace: normalized :: (InnerSpace v, s ~ (Scalar v), Floating s) => v -> v
+ Data.AdditiveGroup: instance (AdditiveGroup v) => AdditiveGroup (a -> v)
+ Data.AdditiveGroup: instance AdditiveGroup ()
+ Data.Basis: decompose' :: (HasBasis v s) => v -> (Basis v -> s)
+ Data.Basis: instance (Eq a, HasBasis u s) => HasBasis (a -> u) s
+ Data.Basis: linearCombo :: (VectorSpace v s) => [(v, s)] -> v
+ Data.Basis: recompose :: (HasBasis v s) => [(Basis v, s)] -> v
+ Data.Maclaurin: fstD :: (HasBasis a s, HasTrie (Basis a), HasBasis b s, HasTrie (Basis b), VectorSpace s s) => (a, b) :~> a
+ Data.Maclaurin: instance (InnerSpace u s, InnerSpace s s, VectorSpace s s, HasBasis a s, HasTrie (Basis a)) => InnerSpace (a :> u) (a :> s)
+ Data.Maclaurin: sndD :: (HasBasis a s, HasTrie (Basis a), HasBasis b s, HasTrie (Basis b), VectorSpace s s) => (a, b) :~> b
+ Data.VectorSpace: instance (HasTrie a, VectorSpace v s) => VectorSpace (a :->: v) s
- Data.Basis: decompose :: (HasBasis v s) => v -> [(s, Basis v)]
+ Data.Basis: decompose :: (HasBasis v s) => v -> [(Basis v, s)]

Files

+ src/Data/ABasis.hs view
@@ -0,0 +1,135 @@+-- WARNING: this module depends on type families working fairly well, and+-- requires ghc version at least 6.9.  I didn't find a way to specify that+-- dependency in the .cabal.+-- +{-# LANGUAGE TypeOperators, TypeFamilies, UndecidableInstances+  , FlexibleInstances, MultiParamTypeClasses+  #-}+{-# OPTIONS_GHC -Wall -fno-warn-orphans #-}+----------------------------------------------------------------------+-- |+-- Module      :  Data.ABasis+-- Copyright   :  (c) Conal Elliott 2008+-- License     :  BSD3+-- +-- Maintainer  :  conal@conal.net+-- Stability   :  experimental+-- +-- Basis of a vector space, as an associated type+-- This module requires ghc-6.10 or later+----------------------------------------------------------------------++module Data.ABasis (HasBasis(..), linearCombo, recompose) where++-- import Control.Applicative ((<$>))+import Control.Arrow (first)+import Data.Either++import Data.AVectorSpace++class VectorSpace v => HasBasis v where+  -- | Representation of the canonical basis for @v@+  type Basis v :: *+  -- | Interpret basis rep as a vector+  basisValue   :: Basis v -> v+  -- | Extract coordinates+  decompose    :: v -> [(Basis v, Scalar v)]+  -- | Experimental version.  More elegant definitions, and friendly to+  -- infinite-dimensional vector spaces.+  decompose'   :: v -> (Basis v -> Scalar v)++-- Defining property: recompose . decompose == id++-- | Linear combination+linearCombo :: VectorSpace v => [(v,Scalar v)] -> v+linearCombo ps = sumV [s *^ v | (v,s) <- ps]++-- Turn a basis decomposition back into a vector.+recompose :: HasBasis v => [(Basis v, Scalar v)] -> v+recompose = linearCombo . fmap (first basisValue)++-- recompose ps = linearCombo (first basisValue <$> ps)+++-- I don't know how to define+-- +--   recompose' :: HasBasis v => (Basis v -> Scalar v) -> v+-- +-- However, I don't seem to use recompose anywhere.+-- I don't even use basisValue or decompose.++instance HasBasis Float where+  type Basis Float = ()+  basisValue ()    = 1+  decompose s      = [((),s)]+  decompose' s     = const s++instance HasBasis Double where+  type Basis Double = ()+  basisValue ()     = 1+  decompose s       = [((),s)]+  decompose' s      = const s++instance ( HasBasis u, s ~ Scalar u+         , HasBasis v, s ~ Scalar v )+      => HasBasis (u,v) where+  type Basis (u,v)     = Basis u `Either` Basis v+  basisValue (Left  a) = (basisValue a, zeroV)+  basisValue (Right b) = (zeroV, basisValue b)+  decompose  (u,v)     = decomp2 Left u ++ decomp2 Right v+  decompose' (u,v)     = decompose' u `either` decompose' v+++decomp2 :: HasBasis w => (Basis w -> b) -> w -> [(b, Scalar w)]+decomp2 inject = fmap (first inject) . decompose++instance ( HasBasis u, s ~ Scalar u+         , HasBasis v, s ~ Scalar v+         , HasBasis w, s ~ Scalar w )+      => HasBasis (u,v,w) where+  type Basis (u,v,w) = Basis (u,(v,w))+  basisValue         = unnest3 . basisValue+  decompose          = decompose  . nest3+  decompose'         = decompose' . nest3++unnest3 :: (a,(b,c)) -> (a,b,c)+unnest3 (a,(b,c)) = (a,b,c)++nest3 :: (a,b,c) -> (a,(b,c))+nest3 (a,b,c) = (a,(b,c))+++instance (Eq a, HasBasis u) => HasBasis (a -> u) where+  type Basis (a -> u) = (a, Basis u)+  basisValue (a,b) = f+    where f a' | a == a'   = bv+               | otherwise = zeroV+          bv = basisValue b+  decompose = error "decompose: not defined on functions"+  decompose' g (a,b) = decompose' (g a) b+++-- Simpler but less efficient:+-- +--   basisValue (a,b) a' | a == a'   = basisValue b+--                       | otherwise = zeroV++-- Just for pointless perversion points:+-- +--   decompose' g = uncurry (\ a b -> decompose' (g a) b)+--   decompose' g = uncurry (\ a -> decompose' (g a))+--   decompose' g = uncurry (decompose' . g)+--   decompose' = uncurry . fmap decompose'+--   decompose' = (fmap uncurry) (fmap decompose')+++{-++---- Testing++t1 = basisValue () :: Float+t2 = basisValue () :: Double+t3 = basisValue (Right ()) :: (Float,Double)+t4 = basisValue (Right (Left ())) :: (Float,Double,Float)++-}
+ src/Data/ALinearMap.hs view
@@ -0,0 +1,44 @@+{-# LANGUAGE TypeOperators, FlexibleContexts, TypeFamilies #-}+{-# OPTIONS_GHC -Wall -fno-warn-orphans #-}+-- {-# OPTIONS_GHC -funbox-strict-fields #-}+-- {-# OPTIONS_GHC -ddump-simpl-stats -ddump-simpl #-}+----------------------------------------------------------------------+-- |+-- Module      :  Data.ALinearMap+-- Copyright   :  (c) Conal Elliott 2008+-- License     :  BSD3+-- +-- Maintainer  :  conal@conal.net+-- Stability   :  experimental+-- +-- Linear maps+-- This version uses ABasis, which requires ghc-6.10 or later.+----------------------------------------------------------------------++module Data.ALinearMap+  ( (:-*) , linear, lapply+  ) where++import Control.Arrow (first)+import Data.Function++import Data.MemoTrie+import Data.AVectorSpace+import Data.ABasis+++-- | Linear map, represented as a memo-trie from basis to values.+type u :-* v = Basis u :->: v++-- TODO: Use a regular function from @Basis u@, but memoize it.++-- | Function (assumed linear) as linear map.+linear :: (VectorSpace u, VectorSpace v, HasBasis u, HasTrie (Basis u)) =>+          (u -> v) -> (u :-* v)+linear f = trie (f . basisValue)++-- | Apply a linear map to a vector.+lapply :: ( VectorSpace u, VectorSpace v, Scalar u ~ Scalar v+          , HasBasis u, HasTrie (Basis u) ) =>+          (u :-* v) -> (u -> v)+lapply lm = linearCombo . fmap (first (untrie lm)) . decompose
+ src/Data/AVectorSpace.hs view
@@ -0,0 +1,147 @@+{-# LANGUAGE MultiParamTypeClasses, FunctionalDependencies +           , TypeOperators, FlexibleInstances, UndecidableInstances+           , TypeFamilies, FlexibleContexts+ #-}+----------------------------------------------------------------------+-- |+-- Module      :   Data.AVectorSpace+-- Copyright   :  (c) Conal Elliott and Andy J Gill 2008+-- License     :  BSD3+-- +-- Maintainer  :  conal@conal.net, andygill@ku.edu+-- Stability   :  experimental+-- +-- Vector spaces+-- +-- This version uses associated types instead of fundeps and+-- requires ghc-6.10 or later+----------------------------------------------------------------------++-- NB: I'm attempting to replace fundeps with associated types.  See+-- NewVectorSpace.hs.  Ran into trouble with type equality constraints not+-- getting propagated.  Manuel Ch is looking into it.+-- +-- Blocking bug: http://hackage.haskell.org/trac/ghc/ticket/2448++module Data.AVectorSpace+  ( module Data.AdditiveGroup+  , VectorSpace(..), (^/), (^*)+  , InnerSpace(..)+  , lerp, magnitudeSq, magnitude, normalized+  ) where++import Data.Complex hiding (magnitude)++import Data.AdditiveGroup+import Data.MemoTrie++infixr 7 *^++-- | Vector space @v@ over a scalar field @s@.  Extends 'AdditiveGroup'+-- with scalar multiplication.+class AdditiveGroup v => VectorSpace v where+  type Scalar v :: *+  -- | Scale a vector+  (*^)  :: Scalar v -> v -> v++infixr 7 <.>++-- | Adds inner (dot) products.+class VectorSpace v => InnerSpace v where+  -- | Inner/dot product+  (<.>) :: v -> v -> Scalar v++infixr 7 ^/+infixl 7 ^*++-- | Vector divided by scalar+(^/) :: (VectorSpace v, s ~ Scalar v, Fractional s) => v -> s -> v+v ^/ s = (1/s) *^ v++-- | Vector multiplied by scalar+(^*) :: (VectorSpace v, s ~ Scalar v) => v -> s -> v+(^*) = flip (*^)++-- | Linear interpolation between @a@ (when @t==0@) and @b@ (when @t==1@).+lerp :: (VectorSpace v, s ~ Scalar v, Num s) => v -> v -> s -> v+lerp a b t = (1-t)*^a ^+^ t*^b++-- | Square of the length of a vector.  Sometimes useful for efficiency.+-- See also 'magnitude'.+magnitudeSq :: (InnerSpace v, s ~ Scalar v) => v -> s+magnitudeSq v = v <.> v++-- | Length of a vector.   See also 'magnitudeSq'.+magnitude :: (InnerSpace v, s ~ Scalar v, Floating s) =>  v -> s+magnitude = sqrt . magnitudeSq++-- | Vector in same direction as given one but with length of one.  If+-- given the zero vector, then return it.+normalized :: (InnerSpace v, s ~ Scalar v, Floating s) =>  v -> v+normalized v = v ^/ magnitude v++instance VectorSpace Double where+  type Scalar Double = Double+  (*^) = (*)+instance InnerSpace  Double where (<.>) = (*)++instance VectorSpace Float  where+  type Scalar Float = Float+  (*^)  = (*)+instance InnerSpace  Float  where (<.>) = (*)++instance (RealFloat v, VectorSpace v) => VectorSpace (Complex v) where+  type Scalar (Complex v) = Scalar v+  s*^(u :+ v) = s*^u :+ s*^v++instance (RealFloat v, InnerSpace v, s ~ Scalar v, AdditiveGroup s)+     => InnerSpace (Complex v) where+  (u :+ v) <.> (u' :+ v') = (u <.> u') ^+^ (v <.> v')++-- Hm.  The 'RealFloat' constraint is unfortunate here.  It's due to a+-- questionable decision to place 'RealFloat' into the definition of the+-- 'Complex' /type/, rather than in functions and instances as needed.++-- instance (VectorSpace u,VectorSpace v, s ~ Scalar u, s ~ Scalar v)+--          => VectorSpace (u,v) where+--   type Scalar (u,v) = Scalar u+--   s *^ (u,v) = (s*^u,s*^v)++instance ( VectorSpace u, s ~ Scalar u+         , VectorSpace v, s ~ Scalar v )+      => VectorSpace (u,v) where+  type Scalar (u,v) = Scalar u+  s *^ (u,v) = (s*^u,s*^v)++instance ( InnerSpace u, s ~ Scalar u+         , InnerSpace v, s ~ Scalar v+         , AdditiveGroup (Scalar v) )+    => InnerSpace (u,v) where+  (u,v) <.> (u',v') = (u <.> u') ^+^ (v <.> v')++instance ( VectorSpace u, s ~ Scalar u+         , VectorSpace v, s ~ Scalar v+         , VectorSpace w, s ~ Scalar w )+    => VectorSpace (u,v,w) where+  type Scalar (u,v,w) = Scalar u+  s *^ (u,v,w) = (s*^u,s*^v,s*^w)++instance ( InnerSpace u, s ~ Scalar u+         , InnerSpace v, s ~ Scalar v+         , InnerSpace w, s ~ Scalar w+         , AdditiveGroup s )+    => InnerSpace (u,v,w) where+  (u,v,w) <.> (u',v',w') = u<.>u' ^+^ v<.>v' ^+^ w<.>w'+++-- Standard instance for an applicative functor applied to a vector space.+instance VectorSpace v => VectorSpace (a -> v) where+  type Scalar (a -> v) = Scalar v+  (*^) s = fmap (s *^)++-- No 'InnerSpace' instance for @(a -> v)@.++instance (HasTrie a, VectorSpace v)+         => VectorSpace (a :->: v) where+  type Scalar (a :->: v) = Scalar v+  (*^) s = fmap ((*^) s)
src/Data/AdditiveGroup.hs view
@@ -40,6 +40,11 @@ sumV :: AdditiveGroup v => [v] -> v sumV = foldr (^+^) zeroV +instance AdditiveGroup () where+  zeroV     = ()+  () ^+^ () = ()+  negateV   = id+ instance AdditiveGroup Double where   zeroV   = 0.0   (^+^)   = (+)@@ -62,17 +67,17 @@ instance (AdditiveGroup u,AdditiveGroup v) => AdditiveGroup (u,v) where   zeroV             = (zeroV,zeroV)   (u,v) ^+^ (u',v') = (u^+^u',v^+^v')-  negateV (u,v)     = (negateV u, negateV v)+  negateV (u,v)     = (negateV u,negateV v)  instance (AdditiveGroup u,AdditiveGroup v,AdditiveGroup w)     => AdditiveGroup (u,v,w) where   zeroV                  = (zeroV,zeroV,zeroV)   (u,v,w) ^+^ (u',v',w') = (u^+^u',v^+^v',w^+^w')-  negateV (u,v,w)        = (negateV u, negateV v, negateV w)+  negateV (u,v,w)        = (negateV u,negateV v,negateV w)   -- Standard instance for an applicative functor applied to a vector space.-instance AdditiveGroup v => AdditiveGroup (u->v) where+instance AdditiveGroup v => AdditiveGroup (a -> v) where   zeroV   = pure   zeroV   (^+^)   = liftA2 (^+^)   negateV = fmap   negateV
src/Data/Basis.hs view
@@ -15,51 +15,76 @@ -- Maintainer  :  conal@conal.net -- Stability   :  experimental -- --- Basis of a vector space, as an associated type+-- Basis of a vector space, as an associated type.+--  This version works with @Data.VectorSpace@, thus avoiding a bug in+--  ghc-6.9.. ---------------------------------------------------------------------- -module Data.Basis-  (-    HasBasis(..)-  ) where+module Data.Basis (HasBasis(..), linearCombo, recompose) where -import Control.Arrow (second)+import Control.Arrow (first) import Data.Either  import Data.VectorSpace  class VectorSpace v s => HasBasis v s where+  -- | Representation of the canonical basis for @v@   type Basis v :: *-  basisValue :: Basis v -> v-  decompose :: v -> [(s, Basis v)]+  -- | Interpret basis rep as a vector+  basisValue   :: Basis v -> v+  -- | Extract coordinates+  decompose    :: v -> [(Basis v, s)]+  -- | Experimental version.  More elegant definitions, and friendly to+  -- infinite-dimensional vector spaces.+  decompose'   :: v -> (Basis v -> s) --- TODO: switch from fundep to associated type.  eliminate the second type+-- TODO: Switch from fundep to associated type.  Eliminate the second type -- parameter in VectorSpace and HasBasis. -- Blocking bug: http://hackage.haskell.org/trac/ghc/ticket/2448+-- Fixed in ghc 6.10. +-- Defining property: recompose . decompose == id++-- | Linear combination+linearCombo :: VectorSpace v s => [(v,s)] -> v+linearCombo ps = sumV [s *^ v | (v,s) <- ps]++-- | Turn a basis decomposition back into a vector.+recompose :: HasBasis v s => [(Basis v, s)] -> v+recompose = linearCombo . fmap (first basisValue)++-- recompose ps = linearCombo (first basisValue <$> ps)+++-- recompose = sumV . fmap (\ (b,s) -> s *^ basisValue b)+ instance HasBasis Float Float where   type Basis Float = ()   basisValue ()    = 1-  decompose s      = [(s,())]+  decompose s      = [((),s)]+  decompose' s     = const s  instance HasBasis Double Double where   type Basis Double = ()   basisValue ()     = 1-  decompose s       = [(s,())]+  decompose s       = [((),s)]+  decompose' s     = const s  instance (HasBasis u s, HasBasis v s) => HasBasis (u,v) s where   type Basis (u,v)     = Basis u `Either` Basis v   basisValue (Left  a) = (basisValue a, zeroV)   basisValue (Right b) = (zeroV, basisValue b)-  decompose (u,v)      = decomp2 Left u ++ decomp2 Right v+  decompose  (u,v)     = decomp2 Left u ++ decomp2 Right v+  decompose' (u,v)     = decompose' u `either` decompose' v -decomp2 :: HasBasis w s => (Basis w -> b) -> w -> [(s, b)]-decomp2 inject = fmap (second inject) . decompose+decomp2 :: HasBasis w s => (Basis w -> b) -> w -> [(b, s)]+decomp2 inject = fmap (first inject) . decompose  instance (HasBasis u s, HasBasis v s, HasBasis w s) => HasBasis (u,v,w) s where   type Basis (u,v,w) = Basis (u,(v,w))   basisValue         = unnest3 . basisValue   decompose          = decompose . nest3+  decompose'         = decompose' . nest3  unnest3 :: (a,(b,c)) -> (a,b,c) unnest3 (a,(b,c)) = (a,b,c)@@ -79,6 +104,15 @@ --  --     type Basis (u,v,w) = Basis u `Either` Basis (v,w) ++instance (Eq a, HasBasis u s) => HasBasis (a -> u) s where+  type Basis (a -> u) = (a, Basis u)+  basisValue (a,b) = f+    where f a' | a == a'   = bv+               | otherwise = zeroV+          bv = basisValue b+  decompose = error "decompose: not defined on functions"+  decompose' g (a,b) = decompose' (g a) b  {- 
src/Data/LinearMap.hs view
@@ -16,18 +16,15 @@  module Data.LinearMap   ( (:-*) , linear, lapply-  -- , inL, inL2, inL3   ) where --- -fglasgow-exts above enables the RULES pragma-+import Control.Arrow (first) import Data.Function  import Data.VectorSpace import Data.MemoTrie import Data.Basis - -- | Linear map, represented a as a memo function from basis to values. type u :-* v = Basis u :->: v @@ -39,20 +36,8 @@ -- | Apply a linear map to a vector. lapply :: (VectorSpace u s, VectorSpace v s, HasBasis u s, HasTrie (Basis u)) =>           (u :-* v) -> (u -> v)-lapply lm u = sumV [s *^ (lm `untrie` b) | (s,b) <- decompose u]+lapply lm = linearCombo . fmap (first (untrie lm)) . decompose   -- TODO: unfst, unsnd, pair, unpair ------ OpenGL stuff.---- I'd rather this code be in a different package.  It's here as a--- temporary bug workaround.  In ghc-6.8.2, I get the following error--- message if the 'LMapDom' instance (below) is compiled in a separate--- module.--- ---     Type indexes must match class instance head
---     Found o but expected Vector2 u
---     In the associated type instance for `:-*'
---     In the instance declaration for `LMapDom (Vector2 u) s'
src/Data/Maclaurin.hs view
@@ -33,14 +33,10 @@     (:>), powVal, derivative --, derivativeAt   , (:~>), dZero, pureD   , fmapD, (<$>>){-, (<*>>)-}, liftD2, liftD3-  , idD -- , fstD, sndD+  , idD, fstD, sndD   , linearD, distrib   -- , (@.)   , (>-<)-  ,(**^), (<*.>)-  -- , HasDeriv(..)-  -- experimental-  -- , liftD3   )      where @@ -127,7 +123,7 @@  -- | Every linear function has a constant derivative equal to the function -- itself (as a linear map).-linearD :: ( HasBasis u s, HasTrie (Basis u){-, VectorSpace (u :> v) s, -}+linearD :: ( HasBasis u s, HasTrie (Basis u)            , VectorSpace v s, VectorSpace s s ) =>            (u -> v) -> (u :~> v) @@ -166,64 +162,41 @@  -- TODO: revise two previous signatures when i've added the VectorSpace instance for u:>v -{-- -- Other examples of linear functions  -- | Differentiable version of 'fst'-fstD :: -- (VectorSpace a s, HasBasis a s, HasTrie (Basis a), HasBasis b s, HasTrie (Basis b)) =>-        ( HasBasis a s, HasTrie (Basis a)+fstD :: ( HasBasis a s, HasTrie (Basis a)         , HasBasis b s, HasTrie (Basis b)-        , HasBasis (a,b) s, HasTrie (Basis (a, b))-        ) =>-        (a,b) :~> a+        , VectorSpace s s+        ) => (a,b) :~> a fstD = linearD fst --- wtf:--- ---   Data/NewMaclaurin.hs:138:7:---       Could not deduce (HasTrie (Basis (a, b)))---         from the context (HasBasis a s,---                           HasTrie (Basis a),---                           HasBasis b s,---                           HasTrie (Basis b),---                           HasBasis (a, b) s,---                           HasTrie (Basis (a, b)))---         arising from a use of `linearD' at Data/NewMaclaurin.hs:138:7-17---       Possible fix:---         add (HasTrie (Basis (a, b))) to the context of---           the type signature for `fstD'---         or add an instance declaration for (HasTrie (Basis (a, b)))---       In the expression: linearD fst---       In the definition of `fstD': fstD = linearD fst---   Failed, modules loaded: Data.MemoTrie, Data.Basis, Data.VectorSpace, Data.AdditiveGroup, Data.NumInstances.---   *Data.Basis> ---- -- | Differentiable version of 'snd'--- sndD :: (VectorSpace b s, HasBasis b s, HasTrie (Basis b), HasTrie (Basis a)) => (a,b) :~> b--- sndD = linearD snd---}+-- | Differentiable version of 'snd'+sndD :: ( HasBasis a s, HasTrie (Basis a)+        , HasBasis b s, HasTrie (Basis b)+        , VectorSpace s s+        ) => (a,b) :~> b+sndD = linearD snd  -- | Derivative tower for applying a binary function that distributes over -- addition, such as multiplication.  A bit weaker assumption than -- bilinearity. distrib :: ( HasBasis a s, HasTrie (Basis a)-           , VectorSpace b s, VectorSpace c s, VectorSpace u s) =>-           (b -> c -> u) -> (a :> b) -> (a :> c) -> (a :> u)+           , VectorSpace b s, VectorSpace c s, VectorSpace u s+           ) => (b -> c -> u) -> (a :> b) -> (a :> c) -> (a :> u)  distrib op u@(D u0 u') v@(D v0 v') =   D (u0 `op` v0) (trie (\ da -> distrib op u (v' `untrie` da) ^+^                                 distrib op (u' `untrie` da) v)) --- TODO: look for a simpler definition of distrib.  See inTrie2. +-- TODO: look for a simpler definition of distrib.  See the applicative+-- instance for @(:->:) a@, or define @inTrie2@.+ -- TODO: This distrib is exponential in increasing degree.  Switch to the -- Horner representation.  See /The Music of Streams/ by Doug McIlroy.  --- I'm not sure about the next three, which discard information- instance Show b => Show (a :> b) where show    = noOv "show" instance Eq   b => Eq   (a :> b) where (==)    = noOv "(==)" instance Ord  b => Ord  (a :> b) where compare = noOv "compare"@@ -233,37 +206,14 @@   negateV = fmapD  negateV   (^+^)   = liftD2 (^+^) -{--instance (HasBasis a s, HasTrie (Basis a), VectorSpace u s) => VectorSpace (a :> u) s where-  (*^) s = fmapD  ((*^) s)--}--(**^) :: (HasBasis a s, HasTrie (Basis a), VectorSpace c s, VectorSpace s s) =>-         (a :> s) -> (a :> c) -> (a :> c)-(**^) = distrib (*^)---- ouch!  InnerSpace one won't work at all, for the same reason as for functions.---- instance (InnerSpace u s) => InnerSpace (a :> u) s where---   (<.>) = distrib (<.>)--(<*.>) :: (HasBasis a s, HasTrie (Basis a), InnerSpace b s, VectorSpace s s) =>-          (a :> b) -> (a :> b) -> (a :> s)-(<*.>) = distrib (<.>)----- The instances below are the one I think we'll want externally.--- However, the ones above allow the definition of @a:>b@ to work out.--- The module "Data.Mac" rewraps to provide the alternate instances.- instance (HasBasis a s, HasTrie (Basis a), VectorSpace u s, VectorSpace s s)          => VectorSpace (a :> u) (a :> s) where-  (*^) = (**^)+  (*^) = distrib (*^) -instance ( InnerSpace u s, InnerSpace s s', VectorSpace s s+instance ( InnerSpace u s, InnerSpace s s, VectorSpace s s          , HasBasis a s, HasTrie (Basis a)) =>      InnerSpace (a :> u) (a :> s) where-  (<.>) = (<*.>)+  (<.>) = distrib (<.>)   -- infixr 9 @.@@ -281,7 +231,7 @@ (>-<) :: (HasBasis a s, HasTrie (Basis a), VectorSpace s s, VectorSpace u s) =>          (u -> u) -> ((a :> u) -> (a :> s))       -> (a :> u) -> (a :> u)-f >-< f' = \ u@(D u0 u') -> D (f u0) ((f' u **^) <$> u')+f >-< f' = \ u@(D u0 u') -> D (f u0) (f' u *^ u')  -- TODO: express '(>-<)' in terms of '(@.)'.  If I can't, then understand why not. 
src/Data/VectorSpace.hs view
@@ -10,7 +10,8 @@ -- Maintainer  :  conal@conal.net, andygill@ku.edu -- Stability   :  experimental -- --- Vector spaces+-- Vector spaces.  Fundep version.  GHC-6.9 isn't quite up to the nicer+-- version in @Data.VectorSpace@, which uses associated types. ----------------------------------------------------------------------  -- NB: I'm attempting to replace fundeps with associated types.  See@@ -111,9 +112,6 @@  -- No 'InnerSpace' instance for @(a->v)@. -instance (HasTrie u, VectorSpace v s, AdditiveGroup (u :->: v))-         => VectorSpace (u :->: v) s where+instance (HasTrie a, VectorSpace v s)+         => VectorSpace (a :->: v) s where   (*^) s = fmap (s *^)---- The 'AdditiveGroup' constraint is implied by the others, thanks to the--- instance in Data.AdditiveGroup.  Why isn't ghc figuring it out?
vector-space.cabal view
@@ -1,5 +1,5 @@ Name:                vector-space-Version:             0.3.1+Version:             0.4 Cabal-Version:       >= 1.2 Synopsis:            Vector & affine spaces, linear maps, and derivatives (requires ghc 6.9) Category:            math@@ -28,35 +28,35 @@ Stability:           experimental build-type:          Simple --- WARNING: Data.Basis depends on type families working fairly well,--- and requires ghc version at least 6.9.  I don't know how to specify--- that dependency in the .cabal.- Library   hs-Source-Dirs:      src   Extensions:             Build-Depends:       base, MemoTrie   Exposed-Modules:     -                     Data.AdditiveGroup                      Data.VectorSpace                      Data.Basis                      Data.LinearMap                      Data.Maclaurin+--                   Data.Horner                      Data.Derivative                      Data.Cross                      Data.AffineSpace                      Data.NumInstances+    +  -- This library relies on type families working as well as in 6.9.+  if impl(ghc < 6.9) {+    buildable: False+  }+  -- More bug fixes in 6.10 allow replacing some fundeps.  After a while,+  -- when 6.10 is widespread, I'll switch over entirely and eliminate the+  -- earlier versions.+  if impl(ghc >= 6.10) {+    Exposed-Modules:+                     Data.AVectorSpace+                     Data.ABasis+                     Data.ALinearMap+  }   ghc-options:         -Wall -O2   ghc-prof-options:    -prof -auto-all  ---  -fno-method-sharing---- Executable Perf---   main-is:           Perf.hs---   build-depends:     base, OpenGL, old-time---   Hs-Source-Dirs:    src, tests/src---   ghc-options:       -Wall -O2---   ghc-prof-options:    -prof -auto-all   ----                   Data.Horner -- For ghc-options: -ddump-simpl-stats -ddump-rules -ddump-simpl -ddump-simpl-phases