Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/unit-testing/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Haskell 为什么我会得到一个“;约束匹配实例声明“;错误?_Haskell - Fatal编程技术网

Haskell 为什么我会得到一个“;约束匹配实例声明“;错误?

Haskell 为什么我会得到一个“;约束匹配实例声明“;错误?,haskell,Haskell,我有以下例子: instance(Typeable crypto,ToCBOR(SIPHash crypto))=>ToCBOR(SIP crypto),其中 -- ... 实例(可键入加密,ToCBOR(哈希加密SIPData))=>ToCBOR(SIPHash加密),其中 -- ... 这会导致以下错误: • The constraint ‘ToCBOR (SIPHash crypto)’ matches an instance declaration instance (Ty

我有以下例子:

instance(Typeable crypto,ToCBOR(SIPHash crypto))=>ToCBOR(SIP crypto),其中
-- ...
实例(可键入加密,ToCBOR(哈希加密SIPData))=>ToCBOR(SIPHash加密),其中
-- ...
这会导致以下错误:

• The constraint ‘ToCBOR (SIPHash crypto)’
    matches an instance declaration
  instance (Typeable crypto, ToCBOR (Hash crypto SIPData)) =>
           ToCBOR (SIPHash crypto)
    -- Defined at src/Cardano/Ledger/Spec/STS/Update/Data.hs:383:10
  This makes type inference for inner bindings fragile; 
    either use MonoLocalBinds, or simplify it using the instance 
• In the context: (Typeable crypto, ToCBOR (SIPHash crypto))
  While checking an instance declaration
  In the instance declaration for ‘ToCBOR (SIP crypto)’
为什么会出现这个错误?编译器错误所指的“匹配”是什么?(据我所知,约束条件是不同的)


PS:我还尝试在没有任何运气的情况下删除了
可键入加密
约束,我想这是因为编译器没有查看实例声明的LHS。

本质上,Haskell告诉您,正如所写的,这些实例将使某些类型的类型推断无法正常工作。
monocalbinds
语言扩展更改了类型系统处理这些场景的方式,因此启用它将允许您的实例按编写的方式运行,但可能会更改代码的语义

Haskell通常对受
let
where
约束的变量使用最通用(最多态)的解释,但如果允许这些类型的实例,可能会有多种不同但同样通用的解释
MonolocalBind
将导致解析器使用不太通用的解释,而不是陷入停顿或做出任意决定。有一篇文章更全面地解释了这个问题,尽管我承认,我没有时间坐下来读它

正如@chi所指出的,GHC让您知道,通过将您的第一个实例替换为:

instance (Typeable crypto, ToCBOR (Hash crypto SIPData)) => ToCBOR (SIP crypto)

我猜这促使你写
实例(可键入密码,ToCBOR(Hash crypto SIPData))=>ToCBOR(SIP crypto)
。在这种情况下,您可以从第二个实例中免费获得
ToCBOR(SipHash crypto)
。这就是我最后做的。我使用了
ConstraintKinds
来避免重复约束:
键入siphascborrept=(Typeable t,ToCBOR(Hash t SIPData))