次のデータ型が定義されていると仮定します。より高い種類の関数?
data X a = X {getX :: a}
data Y a = Y {getY :: a}
data Z a = Z {getZ :: a}
は、3つの別々の機能、getX
、getY
、およびgetZ
が存在しなければなりませんか?このような何か定義された関数があるかもしれないように私には思える:
get :: forall (τ :: (* -> *)) (a :: *). τ a -> a
get (_ x) = x
明らかにこれは有効な標準Haskellのではなく、彼らは解決策を持っている可能性があるように見えるGHCに非常に多くの拡張機能(RankNTypes
、ExistentialQuantification
があります、DataKinds
など)。わずかな量の入力を避ける簡単な理由の他に、レコードソリューションが作成する名前空間の汚染を避けるという利点があります。私は、これは本当にこのように型クラスを使用するよりもちょうどより多くの暗黙的な解決策であると仮定します
class Get f where
get :: f a -> a
しかし、それは一般的な関数を定義する型クラスよりも有用であろうと思われる、それは暗黙的であるという事実ので、多くの場所で、($)
または(.)
と同じ方法で使用できることを意味しています。ですから、私の質問には3つの部分があります:これを達成する方法はありますか、それは良い考えですか?そうでない場合、より良い方法は何ですか?
'get'関数がリストを与えられた場合(つまり、'τ'が '[]'だった場合)はどうなりますか? – duplode
まあ、それはうまくいかないことを暗黙の前提としています。kind *という最終的な型変数を持つ型は、問題の型の単一の引数を取る単一のコンストラクタを持つと仮定する理由はありません。 – Carl