Software Engineering Lecture s12

Menu Menu


Erlang

Erlang : Prolog = Scala : Java

みたいな感じか?

通信、分散処理を重視した言語


Install

otp_src_R13B01.tar.gz などを落して来て、

    tar zxvf otp_src_R13B01.tar.gz 
    cd otp_src_R13B01
    ./configure
    make >& ers &
    tail -f ers

こういう風にすると、log を取りながら、進行状況が見れます。


動かし方

    -module(test).
    -export([fac/1]).
    fac(0) -> 1;
    fac(N) -> N * fac(N-1).

これを test.erl というファイルに書き出す。それを、

    erlc test.erl

で compile する。
    % erl              
    Erlang R13A (erts-5.7) [source] [smp:2:2] [rq:2] [async-threads:0] [kernel-poll:false]
    Eshell V5.7  (abort with ^G)
    1> test:fac(10).
    3628800

というような感じ。


Prolog と Erlang

Erlang は、Prolog の変なところを取って、値を付け加えて、普通にした言語。


Erlang と Scala

どっちも、通信を重視して、通信したデータで場合分けするというのがある。

    -module(math3).
    -export([area/1]).
    area({square, Side}) ->
	Side * Side;
    area({rectangle, X, Y}) ->
	X * Y;
    area({circle, Radius}) ->
	3.14159 * Radius * Radius;
    area({triangle, A, B, C}) ->
	S = (A + B + C)/2,
	math:sqrt(S*(S-A)*(S-B)*(S-C)).

Scala だと case class で書くでしょう。

    2> Thing = {triangle, 6, 7, 8}.
    {triangle,6,7,8}
    3> Thing.
    {triangle,6,7,8}
    4> math3:area(Thing).
    20.33316256758894
    5> Thing = {triangle, 6, 7, 9}.
    ** exception error: no match of right hand side value {triangle,6,7,9}
    6> Thing = {triangle, 6, 7, 8}.
    {triangle,6,7,8}
    7> Thing
    7> .
    {triangle,6,7,8}

一旦、代入した変数の値は変えられない。単一代入。single assignment.


Concurrent Programming

Thread を、比較的簡単な構文で実行できる。

    -module(tut14).
    -export([start/0, say_something/2]).
    say_something(What, 0) ->
	done;
    say_something(What, Times) ->
	io:format("~p~n", [What]),
	say_something(What, Times - 1).
    start() ->
	spawn(tut14, say_something, [hello, 3]),
	spawn(tut14, say_something, [goodbye, 3]).

Thread 間の通信は、! と receive で、Scala と近い。

    -module(tut15).
    -export([start/0, ping/2, pong/0]).
    ping(0, Pong_PID) ->
	Pong_PID ! finished,
	io:format("ping finished~n", []);
    ping(N, Pong_PID) ->
	Pong_PID ! {ping, self()},
	receive
	    pong ->
		io:format("Ping received pong~n", [])
	end,
	ping(N - 1, Pong_PID).
    pong() ->
	receive
	    finished ->
		io:format("Pong finished~n", []);
	    {ping, Ping_PID} ->
		io:format("Pong received ping~n", []),
		Ping_PID ! pong,
		pong()
	end.
    start() ->
	Pong_PID = spawn(tut15, pong, []),
	spawn(tut15, ping, [3, Pong_PID]).

Shinji KONO / Tue Jul 28 14:14:38 2009