使用参数化类型Haskell的模糊类型 [英] Ambiguous type using parameterized types Haskell

查看:154
本文介绍了使用参数化类型Haskell的模糊类型的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个非常简单的函数,它接受一个参数化的数据类型并返回相同的类型:

  { - #LANGUAGE ScopedTypeVariables # - } 

class IntegerAsType a where
value :: a - >整数

newtype(Num a,IntegerAsType n)=> PolyRing a n = PolyRing [a]派生(Eq)

normalize ::(Num a,IntegerAsType n)=> (PolyRing a n) - > (PolyRing a n)
规范r @(PolyRing xs)| (genericLength xs)== len = r
| ... [其他情况]
where len =(value(undefined :: n))

这个想法是,标准化会将PolyRing与任意大小的列表进行比较,然后返回一个新的PolyRing,其长度为n的填充/修改系数矢量,其中n是传入的PolyRing类型的一部分。



我得到错误:

 模糊变量`a0'in约束:
(IntegerAsType a0)由于使用'value'而产生



我看过所有关于这个错误的其他SO帖子,但仍然没有任何内容。即使我删除了所有对'len'的引用(但将其保留在where子句中),也会出现该错误,所以问题出在

 (value(undefined :: n))

这与我用过的方式几乎相同IntegerAsType在其他地方。



当你在这里时,我也在为我现在使用的参数化类型系统的替代品提供建议。特别是,这是一个痛苦,因为我必须为许多不同的值定义IntegerAsType。例如,我们使用类型而不是参数来确保不能添加两个不同多项式环的元素(参数'a'可以确保您不能添加多项式环,mod是相同的多项式,而是在不同的底层环上)。



谢谢

解决方案

c> normalize 不会为<$​​ c $ c>中的类型变量 n 创建范围undefined :: n

  normalize r @(PolyRing xs :: PolyRing an)| ... = ... 
其中len = value(undefined :: n)

或者,您可以在类型签名中为 normalize 使用明确的 forall

  normalize :: forall an。 (Num a,IntegerAsType n)=> (PolyRing a n) - > (PolyRing a n)
规范r @(PolyRing xs)| ... = ...
其中len = value(undefined :: n)

请参阅 http: //www.haskell.org/ghc/docs/7.0.3/html/users_guide/other-type-extensions.html#decl-type-sigs


I have a pretty straightforward function that takes a parameterized data type and returns the same type:

{-# LANGUAGE ScopedTypeVariables #-}

class IntegerAsType a where
  value :: a -> Integer

newtype (Num a, IntegerAsType n) => PolyRing a n = PolyRing [a] deriving (Eq) 

normalize :: (Num a, IntegerAsType n) => (PolyRing a n) -> (PolyRing a n)
normalize r@(PolyRing xs) | (genericLength xs) == len = r
                          | ... [other cases]
           where len = (value (undefined :: n))

The idea is that normalize will take a PolyRing with a list of any size and then return a new PolyRing with a padded/modded coefficient vector of length n, where n is part of the type of the PolyRing passed in.

I'm getting the error:

Ambiguous type variable `a0' in the constraint: 
(IntegerAsType a0) arising from a use of `value'

I've looked at all of the other SO posts on this error, and still have nothing. The error occurs even if I remove all references to 'len' (but keep it in the where clause), so the problem is with

(value (undefined :: n))

which is virtually identical to how I've used IntegerAsType in other places.

While you are at it, I'm also taking suggestions for alternatives to the parameterized type system I'm using now. In particular, it is a pain because I have to define IntegerAsType for lots of different values. We are using the types rather than parameters to ensure, for example, that you can't add two elements of different polynomial rings (the parameter 'a' makes sure you can't add polynomial rings mod the same polynomial but over different underlying rings).

Thanks

解决方案

The signature for normalize doesn't create the scope for the type variable n in undefined :: n.

Try this:

normalize r@(PolyRing xs :: PolyRing a n) | ... = ...
          where len = value (undefined :: n)

Alternatively, you can use an explicit forall in the type signature for normalize:

normalize :: forall a n . (Num a, IntegerAsType n) => (PolyRing a n) -> (PolyRing a n)
normalize r@(PolyRing xs) | ... = ...
      where len = value (undefined :: n)

See http://www.haskell.org/ghc/docs/7.0.3/html/users_guide/other-type-extensions.html#decl-type-sigs

这篇关于使用参数化类型Haskell的模糊类型的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆