fugafuga.write

日々のログ

すごいH本 part38

Shape をShapesモジュールとしてエクスポートする

module Shapes
( Point(..)
, Shape(..)
, area
, nudge
, baseCircle
, baseRect
) where

data Point = ...
...
...

Shape(..)と書くと、Shapeの全ての値コンストラクタがエクスポートされる。後から値コンストラクタを追加する場合にエクスポート文の変更が不要になる。

逆に Shape のエクスポート文の後に括弧を付けないと、Shape 型はエクスポートするけれどもその値コンストラクタは一切エクスポートしないということもできる。

module Shapes
( Point
, Shape
, area
, nudge
, baseCircle
, baseRect
) where

data Point = Point Float Float deriving (Show)
data Shape = Circle Point Float |
             Rectangle Point  Point
  deriving (Show)
...

Main.hsを作成してimportする

import Shapes
main = do
  print $ Circle (Point 10 20) 30

Main.hsをロードするとCircle値コンストラクタが無いよーのエラーとなる

src/Main.hs:3:11: error:
    Data constructor not in scope: Circle :: t0 -> Integer -> a0

src/Main.hs:3:19: error:
    Data constructor not in scope: Point :: Integer -> Integer -> t0
Failed, modules loaded: Shapes.

Main.hsを以下のようにShapesが許可しているものを使用すれば動く

import Shapes
main = do
  print $  nudge (baseCircle 30) 10 20

実行結果

Ok, modules loaded: Main, Shapes.
*Main> main
Circle (Point 10.0 20.0) 30.0

値コンストラクタをエクスポートしないことで何がよいかと言うと、データ型の実装を隠し、抽象度を上げることができる。データを作成する補助関数を定義し、モジュールをインポートしたユーザーにそれを使ってもらうことで、ユーザーはモジュール内部の実装の詳細を知る必要はなくなる。モジュールの作者はエクスポートした関数の振る舞いが同じ限り内部実装を自由に変えることができるようになる。

このようにユーザーに必要なだけの関数をエクスポートし、実装の詳細を隠すようなデータ型のことを抽象データ型という。

所感

抽象化の方法もきちんと用意されていた。

すごいHaskellたのしく学ぼう!

すごいHaskellたのしく学ぼう!

  • 作者: MiranLipovaca
  • 出版社/メーカー: オーム社
  • 発売日: 2017/07/14
  • メディア: Kindle版
  • 購入: 4人 クリック: 9回
  • この商品を含むブログを見る