4

我想学习使用 Deriving Via 来获取更多类型。目前,我经常遇到的一个问题是泛型表示不同时,但如果转换为类型表示更深入到嵌套类型,则它们将是相等的。

简单的例子:

coerce @(Either () ()) @Bool

不起作用,因为Rec0 () :+: Rec0 ()不强制使用U1 :+: U1,即使也:kind! Rep ()给出了 U1。

更复杂的例子

data LeafTree a = Leaf a | Branch [LeafTree a]

是同构的,Free [] a并且由于类似的原因它不会强制。我如何在这些类型之间进行强制转换?我也知道如何使用 DerivingVia 在具有相等 Rep1 的类型之间进行强制转换,如果这有帮助的话。

4

1 回答 1

1

现在使用iso-deriving包,也可以像这样导出 monad 实例:

{-# LANGUAGE TypeOperators, FlexibleInstances, MultiParamTypeClasses, DeriveTraversable, DerivingVia #-}
import Control.Monad.Free
import Iso.Deriving

data LeafTree a = Leaf a | Branch [LeafTree a]
  deriving (Functor)
  deriving (Applicative, Monad) via Free [] `As1` LeafTree

instance Inject (Free [] a) (LeafTree a) where
  inj (Pure x ) = Leaf x
  inj (Free xs) = Branch (fmap inj xs)

instance Project (Free [] a) (LeafTree a) where
  prj (Leaf   x ) = Pure x
  prj (Branch xs) = Free (fmap prj xs)

instance Isomorphic (Free [] a) (LeafTree a)
于 2022-02-17T18:24:05.837 回答