[Haskell-beginners] More Data.Vector fun

Daniel Fischer daniel.is.fischer at web.de
Thu May 13 18:04:50 EDT 2010


On Thursday 13 May 2010 23:26:31, Philip Scott wrote:
> Hey ho,
>
> This should be a quick one, I hope! I am mucking about with the moadic
> initialisers for vectors, and am experiencing all kinds of fun. For
> example, I think I should be able to make a new vector of, say, 3
> thingies* long:
>
> Prelude Data.Vector.Generic.Mutable> new 3
>
> Now of course, poor old haskell does not know what sort of thing I am
> going to put in it yet, so it gets a bit cross:
>
> <interactive>:1:0:
>      Ambiguous type variable `m' in the constraint:
>        `Control.Monad.Primitive.PrimMonad m'
>          arising from a use of `new' at <interactive>:1:0-4
>      Probable fix: add a type signature that fixes these type
> variable(s)
>
> <interactive>:1:0:
>      Ambiguous type variables `v', `a' in the constraint:
>        `MVector v a' arising from a use of `new' at <interactive>:1:0-4
>      Probable fix: add a type signature that fixes these type
> variable(s)
>
>
> Now I have paid very close attention to this 'Probable Fix', but have
> not been able to find out precisely how to specify what sort of vector I
> would like (I guess this is v..) and am even more boggled by 'm'.. I
> guess this is asking what sort of Monad I am going to use to fill it up?

Yes, 'm' is the Monad. All known (by me) instances of PrimMonad are IO and 
(ST s)
'v' is the type of vector you want (very likely MVector [the datatype, not 
the class]), 'a' is the type of elements (Int, Char, ...).

But if you give a type signature, e.g.

Prelude Data.Vector.Generic.Mutable> new 3 :: IO (MVector (PrimState IO) 
Char)

you'll very likely meet "cannot find Show instance for ..."

> An example would be greatly appreciated.
>
> I find the type of 'new' quite interesting:
>
> new
>
>    :: forall (m :: * -> *) (v :: * -> * -> *) a.
>
>       (PrimMonad m, Data.Vector.Generic.Mutable.MVector v a) =>
>       Int -> m (v (PrimState m) a)
>
> So I did a bit of reading up on exstential types,

However, this is not an existential type, just an explicitly universally 
quantified type.

> and I (just about) get
> what 'forall' does, however I don't know what the (m :: * -> *) and  (v
>
> :: * -> * -> *) bits mean. Just telling me what they are called would
>
> probably be enough to get me googling!

Those are kind signatures.

m :: * -> *

means that the type variable m stands for a type constructor which takes 
one type and produces a type from that. Well known examples are [], Maybe, 
IO, (State Int).

v :: * -> * -> *

means that v stands for a type constructor taking two types and producing a 
type. Examples: Either, State.

* is the kind of types (Int, Char, Bool, [Double], Maybe (), ...)
If k1 and k2 are kinds, k1 -> k2 is the kind of type-expressions that take 
a type-expression of kind k1 to produce one of kind k2.
For example, the kind of StateT is

StateT :: * -> (* -> *) -> * -> *

, that means StateT takes
- one type (the state)
- one type constructor producing a type from a type (like IO, Maybe, [])
- another type (the result type)
and produces a type (e.g. StateT Int [] Bool).

>
> I get the feeling I am a bit out of my depth here, but hey ho, I guess
> that's how you learn to swim!
>
> All the best,
>
> Phil
>
> * thingies == things of some type, which doesn't really matter at the
> momant.



More information about the Beginners mailing list