ジェネリックアルゴリズムまたはデータ構造を実装したいとします。「ジェネリック」はポリモーフィックを意味します。どのデータ型でも機能するはずです。たとえば、3つの入力値が等しいかどうかを判断する関数を作成するとします。
特定の(単相)ケースを取り上げると、整数に対してこれを行うことができます。
eq3 :: Int -> Int -> Int -> Bool
eq3 x y z = x == y && y == z
もちろん、上記の定義は他のタイプでも機能することが期待されますが、関数を任意のタイプに適用する必要があることをコンパイラーに指示するだけの場合は、次のようになります。
eq3 :: a -> a -> a -> Bool
eq3 x y z = x == y && y == z
...コンパイラは、==
関数がジェネリックに適用されないと文句を言いますa
:
<interactive>:12:49:
No instance for (Eq a)
arising from a use of `=='
In the first argument of `(&&)', namely `x == y'
In the expression: x == y && y == z
In an equation for `eq3': eq3 x y z = x == y && y == z
a
型が型クラスのインスタンスであることをコンパイラに通知する必要があります。これは、関数が宣言されている場所であることにすでに気付いています。ここで違いを参照してください:Eq
==
eq3 :: Eq a => a -> a -> a -> Bool
eq3 x y z = x == y && y == z
これで、型クラスa
に属するすべての型で均一に動作できる関数ができました。Eq