Reputation: 599
I am trying to study the type classes in haskell. I write the following script and the raised an error. I am unable to understand why the compiler thinks of v as an concrete type while it is just a parameter for class Boxer.
data Box1 a b = Box1 Double a [b]
class Boxer v where
foo :: (v a b) -> Double
instance Boxer (Box1 a b) where
foo (Box1 r s t) = r
it raises an error in line 7:8:
Couldn't match type `v' with `Box1'
`v' is a rigid type variable bound by
the type signature for foo :: v a b -> Double at file1.hs:4:10
Expected type: v a b
Actual type: Box1 a b
Relevant bindings include
foo :: v a b -> Double (bound at file1.hs:7:3)
In the pattern: Box1 r s t
In an equation for `foo': foo (Box1 r s t) = r
Failed, modules loaded: none.
Upvotes: 0
Views: 95
Reputation: 599
The particular problem was being caused by improper indentation. Though there was another thing I was doing wrong. So the following version compiled:
data Box1 a b = Box1 Double a [b]
class Boxer v where
foo :: (v a b) -> Double
instance Boxer Box1 where
foo (Box1 r s t) = r
Upvotes: 1
Reputation: 120711
In your instance, the compiler has to instantiate v
with Box1 a b
. In particular, it has to instantiate v a b
with something like (Box1 a b) a b
– except both a
variables come from a different place; they're actually disambiguated to (Box1 a b) a1 b1
. Which is the same as Box1 a b a1 b1
.
foo :: Box1 a b a1 b1 -> Double
Does that make any sense?
The problem is that you're confusing a (type) function, namely Box1
, with the result of applying said function to some type arguments. The kinds don't match:
GHCi> :k Boxer
Boxer :: (* -> * -> *) -> Constraint
GHCi> :k (Box1 Int String)
Box1 Int String :: *
* -> * -> *
is the kind of a type function / type constructor with two arguments, so that's what Boxer
needs. Whereas Box1 a b
is simply a type, with no arguments. Doesn't match! OTOH,
GHCi> :k Box1
Box1 :: * -> * -> *
Upvotes: 2