使用Data.Vector“推断类型不明确”错误

时间:2014-12-22 04:59:29

标签: haskell

以下代码无法编译,并在下面给出了错误消息。 f应该只是一个状态monad,在运行时创建一个长度为1的向量,其中包含一个int" 42"。我怀疑在rununstream之间发生了一些歧义,很像show . read,但我无法弄清楚如何解决它:

{-# LANGUAGE NoMonomorphismRestriction #-}

import Data.Vector.Generic.New (run, unstream)
import Data.Vector.Fusion.Stream (singleton)

f = run . unstream . singleton $ (42 :: Int)

main = return ()

错误:

main.hs:6:1:

Could not deduce (Data.Vector.Generic.Base.Vector v0 Int)
  arising from the ambiguity check for `f'
from the context (Data.Vector.Generic.Base.Vector v Int)
  bound by the inferred type for `f':
             Data.Vector.Generic.Base.Vector v Int =>
             GHC.ST.ST s (Data.Vector.Generic.Base.Mutable v s Int)
  at sort.hs:6:1-44
Possible fix:
  add an instance declaration for
  (Data.Vector.Generic.Base.Vector v0 Int)
When checking that `f'
  has the inferred type `forall (v :: * -> *) s.
                         Data.Vector.Generic.Base.Vector v Int =>
                         GHC.ST.ST s (Data.Vector.Generic.Base.Mutable v s Int)'
Probable cause: the inferred type is ambiguous

main.hs:6:1:

Could not deduce (Data.Vector.Generic.Base.Mutable v0
                  ~ Data.Vector.Generic.Base.Mutable v)
from the context (Data.Vector.Generic.Base.Vector v Int)
  bound by the inferred type for `f':
             Data.Vector.Generic.Base.Vector v Int =>
             GHC.ST.ST s (Data.Vector.Generic.Base.Mutable v s Int)
  at sort.hs:6:1-44
NB: `Data.Vector.Generic.Base.Mutable' is a type function, and may not be injective
Expected type: Data.Vector.Generic.Base.Mutable v s Int
  Actual type: Data.Vector.Generic.Base.Mutable v0 s Int
Expected type: GHC.ST.ST
                 s (Data.Vector.Generic.Base.Mutable v s Int)
  Actual type: GHC.ST.ST
                 s (Data.Vector.Generic.Base.Mutable v0 s Int)
When checking that `f'
  has the inferred type `forall (v1 :: * -> *) s1.
                         Data.Vector.Generic.Base.Vector v1 Int =>
                         GHC.ST.ST s1 (Data.Vector.Generic.Base.Mutable v1 s1 Int)'
Probable cause: the inferred type is ambiguous

2 个答案:

答案 0 :(得分:1)

您通常可以通过附加类型注释来解决这些歧义。在这种情况下,问题是,"当unstream创建Vector v a时,我应该使用哪个New v a实例?"。这可以通过在rununstream上添加注释来解决,但看起来好像unstream上的注释会更少(手指)输入。像这样:

f = run . (unstream :: Stream Int -> New {- put something concrete here -} Int) . singleton $ 42

答案 1 :(得分:1)

这是show . read问题,但有一点麻烦。

我们在这里写的两个函数是

unstream :: forall s v a. (Vector v) => Stream a -> New v a
run :: forall s v' a'. New v' a' -> ST s (Mutable v' s a')

组合它们会产生New v a ~ New v' a',并且由于New是一种数据类型,因此它是单射的;因此我们有v ~ v'a ~ a',用于:

run . unstream :: forall s v a. (Vector v) => Stream a -> ST s (Mutable v s a)

但是v的选择未指定类型Stream a -> ST s (Mutable v s a),因为Mutable是一个类型系列,因此不是单射的。这就像show . read :: forall a. (Show a, Read a) => String -> String;它更难看,因为v似乎出现在类型中。

考虑在更具体的类型中使用它时会发生什么,例如

run . unstream :: forall s. Stream Int -> ST s (MVector s a)

没有办法知道v应该来自Mutable v ~ MVector

所有这些都提示了一种多态地输入run . unstream . singleton的方法,而不需要预先选择v,只需要在呼叫站点传递它:

{- LANGUAGE ScopedTypeVariables #-}

f :: forall s v a. (Vector v a) => Proxy v -> a -> ST s (Mutable v s a)
f _ = run . (unstream :: Stream a -> New v a) . singleton