2013年1月16日水曜日

Haskellのinstance、class、 dataそれぞれとtype-parameterの組み合わせ


まず、Num aクラスのinstanceを見てみます。
class Num a where
  (+) :: a -> a -> a
  (*) :: a -> a -> a
  (-) :: a -> a -> a
  negate :: a -> a
  abs :: a -> a
  signum :: a -> a
  fromInteger :: Integer -> a
instance Num Integer
instance Num Int
instance Num Float
instance Num Double
Num aはtype-parameterがありますので、Numはtype constructorである。したがって、
foo::Num
foo = 3
ということはできません。

クラス中の演算子+、*、-及び関数negate、abs、signumを使いたい場合は、
クラス中のinstanceになるしかない。たとえば、
foo::Float
foo = 3
下のような感じで考えるほうがいいかもしれません。(実際はないですけど・・・)
data Float = Float deriving (Num)
FloatがNumの性質を持たせるみたいに。
ほかのNum aインスタンスInteger、Int、Doubleも同じく、
演算子+、*、-及び関数negate、abs、signumを使えるはずです。

つぎは、data中のtype-parameterを見てます。
data Maybe a = Nothing | Just a 
instance Eq a => Eq (Maybe a)
instance Monad Maybe
instance Functor Maybe
instance Ord a => Ord (Maybe a)
instance Read a => Read (Maybe a)
instance Show a => Show (Maybe a)
上の推理によって、type-parameterがあるから、こういうこと
foo::Maybe
foo = Just 3
はできません。
幸いMaybeはalgebraic data typeで宣言してますので、
aに型をつけて、さらに|の左か右を一つvalue constructorを選ぶだけで
foo,bar::Maybe Int
foo = Just 1
bar = Just 1
fooとbarがインスタンスEq aの性質を持つことになります。
*Main> foo == bar
True

今度はtype constrain (=>)についてみてみます。

0 件のコメント:

コメントを投稿