如何在不使用-XUndecidableInstances的情况下绕过功能依赖的覆盖条件 [英] How to get around the Coverage Condition for Functional Dependencies without using -XUndecidableInstances

查看:149
本文介绍了如何在不使用-XUndecidableInstances的情况下绕过功能依赖的覆盖条件的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

Wen使用函数依赖关系时,经常碰到 Coverage Condition 。可以使用 UndecidableInstances 来解除它,但我通常会尽量远离该扩展名。



这里是一个有点人为的例子,没有 UndecidableInstances

  { - #语言MultiParamTypeClasses,FunctionalDependencies,FlexibleInstances# - } 

data结果=结果字符串
派生(Eq,Show)

数据参数ab =参数ab

class可应用ab | a - > b其中
apply :: a - > b - >结果

实例可应用(参数ab)(a - > b - >结果)其中
(参数ab)`apply` f = fab
UndecidableInstances
$ b> ):
$ b $

  { - #语言MultiParamTypeClasses,FunctionalDependencies,FlexibleInstances,UndecidableInstances# - } 

数据结果a =结果a
导出(Eq,Show)

data参数ab =参数ab

class可应用abc | a - > b c其中
apply :: a - > b - >结果c

实例可应用(参数ab)(a - > b - >结果c)c其中
(参数ab)`apply` f = fab

我认为,因为 b c 都是由 a 决定的,更通用的代码不应该引起任何问题,所以我的问题:


  1. 在这里使用 UndecidableInstances 有任何可能的问题

  2. 我可以建模上述场景而不依赖于 UndecidableInstances (也许与类型系列?)


解决方案

没有很大的理由远离 UndecidableInstances 。可能发生的最糟糕的事情是类型检查器开始循环(并且告诉你这个问题,我想)。你可以使覆盖条件变得越来越聪明,但它不会做你想做的所有事情,因为这是不可判定的。


Wen using functional dependencies, I frequently hit the Coverage Condition. It is possible to lift it with UndecidableInstances, but I usually try to stay away from that extension.

Here is a somewhat contrived example, that works without UndecidableInstances:

{-# Language MultiParamTypeClasses, FunctionalDependencies, FlexibleInstances #-}

data Result = Result String
  deriving (Eq, Show)

data Arguments a b = Arguments a b

class Applyable a b | a -> b where
  apply :: a -> b -> Result

instance Applyable (Arguments a b) (a -> b -> Result) where
  (Arguments a b) `apply` f = f a b

When I make the result type more generic, the Coverage Condition fails (hence requiring UndecidableInstances):

{-# Language MultiParamTypeClasses, FunctionalDependencies, FlexibleInstances, UndecidableInstances #-}

data Result a = Result a
  deriving (Eq, Show)

data Arguments a b = Arguments a b

class Applyable a b c | a -> b c where
  apply :: a -> b -> Result c

instance Applyable (Arguments a b) (a -> b -> Result c) c where
  (Arguments a b) `apply` f = f a b

I thought that because b and c are both determined by a, the more generic code should not cause any problems, so my questions:

  1. Are there any possible issues with using UndecidableInstances here
  2. Can I model the above scenario without relying on UndecidableInstances (maybe with type families?)

解决方案

There's no big reason to stay away from UndecidableInstances. The worst that can happen is that the type checker starts looping (and tells you about it, I think). You can make the coverage condition more and more clever, but it will never do everything you could want since that's undecidable.

这篇关于如何在不使用-XUndecidableInstances的情况下绕过功能依赖的覆盖条件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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