为傻瓜键入家庭

时间:2015-12-27 16:44:19

标签: haskell

有人可以给出一个超级简单(几行)的例子,以便基本了解哪些类型的家族可以使用,以及它们是什么?

2 + 2类型家庭的例子?

1 个答案:

答案 0 :(得分:7)

以下是一个例子:

{-# Language TypeFamilies, DataKinds, KindSignatures, GADTs, UndecidableInstances #-}

data Nat = Z | S Nat

type family Plus (x :: Nat) (y :: Nat) :: Nat where
  Plus 'Z y = y
  Plus ('S x) y = 'S (Plus x y)

data Vec :: Nat -> * -> * where
  Nil :: Vec 'Z a
  Cons :: a -> Vec n a -> Vec ('S n) a

append :: Vec m a -> Vec n a -> Vec (Plus m n) a
append Nil ys = ys
append (Cons x xs) ys = Cons x (append xs ys)

请注意,类型系列的许多/最有趣的应用程序需要UndecidableInstances。你不应该害怕这种扩展。

另一种有用的类型系列是与类相关联的类型。对于一个非常人为的例子,

class Box b where
  type Elem b :: *
  elem :: b -> Elem b

Box的一个实例是一种可以从中抽出的东西。例如,

instance Box (Identity x) where
  type Elem (Identity x) = x
  elem = runIdentity

instance Box Char where
  type Elem Char = String
  elem c = [c]

现在elem (Identity 3) = 3elem 'x' = "x"

您还可以使用类型族来制作奇怪的skolem变量。这最好在尚未发布的GHC 8.0.1中完成,它看起来像

type family Any :: k where {}

Any是一种奇特的类型。它是无人居住的,它不能(特别)是一个类的实例,它是多重的。事实证明这对某些目的非常有用。此特定类型被宣传为unsafeCoerce的安全目标,但Data.Constraint.Forall使用类似的类型系列用于更有趣的目的。