先ほど、行列の数値を集める小さなプログラムを作成しました - data Matrix = Matrix [[Int]]
角で始まり - [Direction]
すべてその後、私はこの機能を使用LeftUp
とRight
haskellの多型 - 異なる名前を付けずに関数の複数のバージョンを使用する
turnLUR :: Transformable a => (Corner, Direction) -> a -> a
に - の3つのタイプが、私は与えられたコーナーと方向を回転させる変換関数を生成する機能を有するクラスTransformable
のインスタンスであります「収穫」マトリックス内のすべての番号に:
harvest :: Matrix → [(Corner,Direction)] → [Int]
harvest _ [] = []
harvest (Matrix []) _ = []
harvest as (cd:csds) = b ++ harvest (Matrix bs) csds' --cd = (Corner,Direction)
where f1 = turnLUR cd -- Matrix -> Matrix
f2 = turnLUR cd -- Corner -> Corner
f3 = turnLUR cd -- Direction -> Direction
Matrix (b:bs) = f1 as -- b = first line of [[Int]]
fcfd (c,d) = (f2 c,f3 d)
csds' = map fcfd csds
今私は
f1
、
f2
と
f3
代わりに一つの機能を使用するので書き留めなければならないのですなぜ、私の質問
f
3回(!私の心の中でDRYに保ちます) -
Corners
,
Directions
、および
Matrix
の3種類すべてが
class Transformable
のインスタンスです。
「同じ」機能の3つのバージョンを作成することなく、そのコードをどのように書くことができますか?
monomorphismの制限は、無意味な形式で書かれた関数(関数ではない値だけでなく)にも影響するので、明示的なパラメータを使って 'f'を定義すると、型署名を与えないでください。 – sepp2k
型署名 'f :: Transformable a => a - > a'は、型署名に指定された関数を保持します。それがなければ、コンパイラは 'f'が' Matrix - > Matrix'型であることをその最初の用法として推論します。これを明確にしていただきありがとうございます。特に私は署名がこの単形体の制限を解決できるかどうか分からなかった。 – epsilonhalbe