16

私は型クラスをいじっていて、これを作りました:

class Firstable f where
  fst :: f a -> a

class Secondable f where
  snd :: f a -> a

次に、の実装を追加しようとしたところ、次の(,)ことができることに気付きました。

instance Secondable ((,) a) where
  snd (x,y) = y

私はこれがうまくいくと確信しています。なぜなら、その型を持っSecondableている種類(* -> *)が必要だからです。しかし、バインドされた変数がどこにあるのかを実装する((,) a)方法がわかりません。Firstable((,) * a)*

instance Firstable (flip (,) a) where ...

Haskellでこれを行う方法はありますか? できれば拡張子なしですか?

4

3 に答える 3

10

あなたはそのような型族を使うことができます(エドワードが書いたものの別の見方):

{-# LANGUAGE TypeFamilies #-}

class Firstable a where
  type First a :: *
  fst :: a -> First a

class Secondable a where
  type Second a :: *
  snd :: a -> Second a

instance Firstable (a,b) where
  type First (a, b) = a
  fst (x, _) = x

instance Secondable (a,b) where
  type Second (a, b) = b
  snd (_, y) = y
于 2012-06-05T16:16:43.477 に答える
1

パラメトリシティの保証がより悪いバージョンは、MPTCSとFundeps、またはTypeFamiliesで使用できます。

type family Fst p
type instance Fst (a,b) = a
type instance Fst (a,b,c) = a

..。

class First p where
   fst :: p -> Fst p

instance Fst (a,b) where
   fst (a,_) = a

instance Fst (a,b,c) where
   fst (a,_,_) = a

..。

ただし、最終的には、いくつかの拡張機能を使用する必要があります。

于 2012-06-05T16:12:16.560 に答える
1
class Firstable f where
    fst :: f a b -> a

class Secondable f where
    snd :: f a b -> b
于 2012-06-05T15:31:07.617 に答える