1
votes

I defined :

type Network = [(Matrix Double,Vector Double)]

where Matrix and Vector are from the hmatrix library. From the documentation of hmatrix it seems to me that Matrix Double and Vector Double are already instances of Num. Since I need to add and subtract Networks quiet a lot I also want Network to be an instance of Num. I tried

instance Num Network where
  (+) = zipWith (\(m,v) (n,w) -> (m+n,v+w))
  (-) = zipWith (\(m,v) (n,w) -> (m-n,v-w))
  (*) = zipWith (\(m,v) (n,w) -> (m*n,v*w))

but I am getting the error : Illegal Instance declaration.

1
You need to turn on the FlexibleInstances language extension to create instances over type synonyms like the one you’ve written. The GHC error message might even suggest this (along with TypeSynonymInstaces, though FlexibleInstnaces implies the former).Alexis King
@AlexisKing: Could you put that as an answer? It actually answers the question and it'll have better visibility.Tikhon Jelvis
Please, just don't do this. It's not a good idea. A vector is not a number; element-wise multiplication doesn't have semantics that make sense for general vectors. And almost certainly not for networks, either. It may well make sense to give it a VectorSpace instance, though, but you should definitely wrap it in a newtype.leftaroundabout
Note that when you define an instance you should define all the operations of the class. This includes, for example, signum and abs. Failing to do so may cause your programs to crash because some piece of code actually uses these and they end up undefined.Bakuriu

1 Answers

5
votes

Alexis King's comment is correct to get your current code to compile. However, it might be better practice to make a newtype for Network - that way you don't need to use any language extensions at all.

newtype Network = Network [(Matrix Double,Vector Double)]

instance Num Network where
  (Network n1) + (Network n2) = Network $ zipWith (\(m,v) (n,w) -> (m+n,v+w)) n1 n2
  (Network n1) - (Network n2) = Network $ zipWith (\(m,v) (n,w) -> (m-n,v-w)) n1 n2
  (Network n1) * (Network n2) = Network $ zipWith (\(m,v) (n,w) -> (m*n,v*w)) n1 n2