本文介绍了多参数类型同义词实例的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我试图找出是否有可能(以及如何)为多参数类型同义词定义类实例。

例如:



  { - #LANGUAGE MultiParamTypeClasses,FlexibleInstances# - } 

type F ab = a - > b
data DF a b = DF(a - > b)

class C c a b其中
doc :: c a b - > a - > b

它适用于多参数类型的实例:

 实例C DF ab其中
doc(DF f)x = fx

但对于同义词类型无效:

   - 错误:
-
- 类型同义词`F'应该有2个参数,但是没有给出
- 在`CF a b'的实例声明中
-
实例CF ab其中
doc fx = fx

是否可以定义一个类型类实例为 F

解决方案

类型同义词通常必须完全适用于使用它们,特别是。



请注意,如果您可以eta-缩小类型同义词足够一个实例是可能的;它是必须完全应用的同义词,而不是它所指的类型。所以这是可行的:

  type F =( - >)

实例CF ab其中
doc fx = fx

有,但它在这里没有帮助 - 它只允许您执行诸如将部分应用类型同义词作为另一类型同义词的类型参数。一切都必须完全展开才能使用。



要看出这个限制有必要的一个原因,请考虑以下类型的同义词:

  type Flip fab = fba 

下面的例子:

pre $ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $
fmap f(Left x)= Left(fx)

回想一下,还有一个实例 Functor(或者a)它可以做同样的事情,除了镜像。两者都是明智的 Functor 实例。

请记住,与 newtype 不同,类型同义词被认为与它们引用的类型相同,表达式 fmap的值不是(Right True :: Bool Bool)是?


I'm trying to figure out if it's possible (and how) to define class instances for multi-parameter type synonyms.

For example:

{-# LANGUAGE MultiParamTypeClasses, FlexibleInstances #-}

type F a b = a -> b
data DF a b = DF (a -> b)

class C c a b where
    doc :: c a b -> a -> b

It works for a multi-param type instance:

instance C DF a b where
    doc (DF f) x = f x

But it doesn't work for type synonyms:

-- ERROR:
--
-- Type synonym `F' should have 2 arguments, but has been given none
-- In the instance declaration for `C F a b'
--
instance C F a b where
    doc f x = f x

Is it possible to define a type class instance for F?

解决方案

It's not possible as written. Type synonyms must in general be fully applied to use them, especially as a type class parameter.

Note that if you can eta-reduce the type synonym enough an instance is possible; it's the synonym which must be fully applied, not the type it refers to. So this would work:

type F = (->)

instance C F a b where
    doc f x = f x

There is a LiberalTypeSynonyms extension that relaxes some of the rules about expanding type synonyms, but it doesn't help here--it only lets you do things like give a partially-applied type synonym as a type parameter of another type synonym. Everything must still be fully expanded to use otherwise.

To see one reason why this restriction is necessary, consider the following type synonym:

type Flip f a b = f b a

And the following instance:

instance Functor (Flip Either a) where
    fmap _ (Right x) = Right x
    fmap f (Left x) = Left (f x)

Recall that there's also an instance Functor (Either a) which does the same thing, except mirrored. Both are sensible Functor instances.

Keeping in mind that unlike newtype, type synonyms are considered the same as the type they refer to, what should the value of the expression fmap not (Right True :: Either Bool Bool) be?

这篇关于多参数类型同义词实例的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

08-22 19:55