Re:Start

いまはディレクターやってます

いよいよモジュールを作るよ

今日は、learn you some erlangの第4章であるモジュール!!
http://www.ymotongpoo.com/works/lyse-ja/ja/04_modules.html

モジュールを作る

  • ファイルの拡張子は .erl
  • 関数の形
Name(Args) -> Body
  • Bodyはピリオドで終わる
  • returnは何の効果ももたらさない
  • 最後の式の値が返される。

サンプルコード

  • 頭にimport

文を書く事で、io:formatという形式でなく、formatで書く事ができるようになるが、別モジュールに同じメソッドが定義されている場合もあり、可読性が下がるので、erlangの流儀では、importは基本使わないらしい。

  • module()文でファイル名を定義する
  • export()文で公開する(他でも使う)モジュールを定義する ← これはすごく忘れそうだ。
    • リストの中に、モジュール名/数字の順番で追加していく
  • コメント文は1行単位のみで、頭に%をつける
%-import(io,[format/2]).
-module(useless).
%-export([add/2],[greet_and_add_two/1]).
-export([add/2,hello/0,greet_and_add_two/1]).

add(A,B) ->
  A + B.

%% Shows greetings.
%% io:format/1 is the standard function used to output text.
hello() ->
  io:format("Hello, world!~n").

greet_and_add_two(X) ->
  hello(),
  add(X,2).

コンパイルする

  • 作成したモジュールは、シェル上でコンパイルすると使えるようになる
  • シェル上では、cd(ファイルの場所)で、指定した場所に移動できる
$ erl
Erlang R15B02 (erts-5.9.2) [source] [smp:2:2] [async-threads:0] [hipe] [kernel-poll:false]

Eshell V5.9.2  (abort with ^G)
1> c(useless).
{ok,useless}
  • 無事にコンパイルできたので、useless.beamというファイルが作成された。
  • 使ってみる
2> useless:add(7,2).
9
3> useless:hello().
Hello, world!
ok
4> useless:greet_and_add_two(-3).
Hello, world!
-1
5> useless:not_a_real_function().
** exception error: undefined function useless:not_a_real_function/0
  • 定義されていないファンクションを呼び出した場合はエラー
  • コンパイル時に引数を追加してテストしやすくしたりする。
6> compile:file(useless,[debug_info,export_all]).
{ok,useless}
7> c(useless,[debug_info,export_all]).
{ok,useless}
  • ファイルに直接追加することも可能

useless.erl

-compile([debug_info,export_all]).
  • hipe:c()コマンドでコンパイルした場合は、ネイティブで使えるようになる!!
  • 速度も20%アップするが...
  • モジュールのめたデータを取得する
  • ファイルの頭にモジュール属性を追加することで、たとえば著者情報等を追記できる。 ex. -author("An Erlang Champ").
  • どのユニットテストがよいか関数にアノテーションつけると、 スクリプトはモジュール属性をみて、アノテーションがある関数を探して、それらの関数に対する警告を出してくれたりとか!
  • vsnはバージョンNoのことで、ソース内で自分で指定することもできる。 -vsn(VersionNumber).
9> useless:module_info().
[{exports,[{add,2},
           {hello,0},
           {greet_and_add_two,1},
           {module_info,0},
           {module_info,1}]},
 {imports,[]},
 {attributes,[{vsn,[296174539721071843666185210011547328263]}]},
 {compile,[{options,[debug_info,export_all]},
           {version,"4.8.2"},
           {time,{2012,11,1,22,42,39}},
           {source,"/Users/araichie/workspace/erlang/useless.erl"}]}]
10> useless:module_info(attributes).
[{vsn,[296174539721071843666185210011547328263]}]

その他のルール

  • 循環参照は避けよう! モジュールAはモジュールA自身を呼び出しているモジュールBを呼ぶべきではない。

振り返り

Java,ruby,Python,PHPと色々触ってきたけれど、どれと似ているという感覚が生まれずに、本当にコードを書いている気分がする。数学的な所が試されるというか適度な緊張感が合って、いいかもしれない。
ただ、きっとはまりそうw