What is a type "t" in an inferred Haskell type signature?
I wrote a function f
, which I use in a foldM
:
foldM (f xs) [] ids
...
f xs acc id = case lookup id xs of
Just x -> return $ acc ++ [(id, x)]
Nothing -> throwError $ TypeError "Cannot project nonexisting field"
the type signature I wrote for it is:
[(String, Value)] -> [(String, Value)] -> String -> EvalMonad [(String, Value)]
then I decided to delete the type signature, since the function is simple and descriptive enough as it is. When I used hdevtools to get the inferred type, I got
[(t, t)] -> [(t, t)] -> t -> m [(t, t)]
What is this? I am guessing that t is different from the usual a
or b
you commonly see. The first and second element of the tuple are not the same type (no, SValue is not a type synonym of String), while this signature implies that constraint. Also, why is there no class constraint on the monad m? I am not using the whole EvalMonad stack here, but m
should at least be an instance of MonadError
.
I used ghci to check the inferred type of your code, like so:
f typeError xs acc id = case lookup id xs of
Just x -> return $ acc ++ [(id, x)]
Nothing -> throwError $ typeError "Cannot project nonexisting field"
(note that I made the fixed TypeError
into an extra argument typeError
so I didn't have to have a definition for it)
The type I got was:
f :: (Eq t, MonadError e m) =>
([Char] -> e) -> [(t, t1)] -> [(t, t1)] -> t -> m [(t, t1)]
So I'm not sure why you're getting something a type with [(t, t)]
, or without the constraints. t
in a type signature is indeed the same as a
or b
; in a type, any identifier starting with a lowercase letter is a type variable, and multiple repetitions of a single such identifier within a single type represent the same type variable.
上一篇: 输入实例函数的推理