型推論アルゴリズムが埋める「空白」を含む Haskell 値に型署名を提供することは可能ですか?
コンテキストの非常に不自然な例:
m = return ('I', (("don't", "really"), "care", ["what", "this"], "type"), "is")
b = isJust m
これは機能します。isJust m
inの使用はb
の型m
を beMaybe <something>
にm
制約し、 の定義は の型m
を be<something> (Char, ((String, String), String, [String], String), String)
に制約し、コンパイラはこれら 2 つの情報を組み合わせて の正確な型を計算しm
ます。
Maybe
しかし、特定の関数を に適用していないm
ので、ポリモーフィックであることを止めるために手動の型シグネチャが必要になりますreturn
。私はこれを言うことはできません:
m :: Maybe a
m = return ('I', (("don't", "really"), "care", ["what", "this"], "type"), "is")
それは間違っているからです。型はMaybe a
すべてa
ではありません。コンパイラに推論さMaybe a
せa
たいものもあります。コンパイラがこれを行うのに十分な情報がプログラムにあり、最初の例から、コンパイラが型に複数の制約をまとめることができることがわかります。一緒にそれらはタイプを完全に指定します。
私が望むのは、のような「これは厳密な型変数である」という意味ではなく、「ここに何が入るかを理解する」という意味m :: Maybe _
のような型を与えることができるようにすることです。_
m :: Maybe a
このようなことを言う方法はありますか?私が見ることができる代替手段は、明示的に完全な型を与えています:
m :: Maybe (Char, ((String, String), String, [String], String), String)
m = return ('I', (("don't", "really"), "care", ["what", "this"], "type"), "is")
または、式の一部に型シグネチャを与えると、型シグネチャの一部を制約する効果がありますが、次のようにMaybe
はなりません。a
m = (return :: a -> Maybe a) ('I', (("don't", "really"), "care", ["what", "this"], "type"), "is")
または、明示的な型署名なしで残しm
、制約する未使用の追加の定義を導入しますm
。
m = return ('I', (("don't", "really"), "care", ["what", "this"], "type"), "is")
b = isJust m
または、単相関数を直接使用します。
m = Just ('I', (("don't", "really"), "care", ["what", "this"], "type"), "is")
明らかに、これは に固有のものでも、型コンストラクターMaybe
の引数にも固有のものではありません。「この値はモナドのモナドです」と言いたいのではなく、「この値はモナドのモナドです」、または「これは他の型への関数です」とは言わず* -> *
に言いたいことが想像できます。関数から他の型へ`.Int
Int
Int
Int
私は主に、読みにくい回避策 ( return
. 私の目標が単純に追加の型情報をコンパイラに取得して、あいまいな型変数についてそれを黙らせることである場合、それを行う方法は無数にあります。