Erlang Language
プロセス
サーチ…
プロセスの作成
spawn
関数を呼び出すことによって、新しい並行プロセスを作成します。 spawn
関数は、プロセスとして評価される関数Fun
をパラメータとして取得します。 spawn
関数の戻り値は、作成されたプロセス識別子(pid)です。
1> Fun = fun() -> 2+2 end.
#Fun<erl_eval.20.52032458>
2> Pid = spawn(Fun).
<0.60.0>
また、 spawn/3
を使用して、モジュールから特定の関数、すなわちspawn(Module, Function, Args)
を実行するプロセスを開始spawn/3
こともできspawn/3
。
または、 spawn/2
またはspawn/4
同様に使用して、別のノードspawn(Node, Fun)
つまりspawn(Node, Module, Function, Args)
spawn(Node, Fun)
またはspawn(Node, Module, Function, Args)
プロセスを開始します。
メッセージの受け渡し
2つのerlangプロセスは互いに通信することができ、 メッセージ・パッシングとも呼ばれます 。
このプロシージャは、メッセージを送信した後に送信プロセスが停止しないという形で非同期です。
メッセージを送信する
これはPid ! Message
、 Pid
は有効なプロセス識別子(pid)、 Message
は任意のデータ型の値です。
各プロセスには、受信したメッセージを受信した順序で含む「メールボックス」があります。この「メールボックス」は、 flush/0
関数でビルドすると空にできます。
メッセージが既存のプロセスに送信されていない場合、メッセージはエラーなしで破棄されます。
例は次のようになります。self self/0
は現在のプロセスのpidを返し、 pid/3
はpidを生成します。
1> Pidsh = self().
<0.32.0>
2> Pidsh ! hello.
hello
3> flush().
Shell got hello
ok
4> <0.32.0> ! hello.
* 1: syntax error before: ’<’
5> Pidsh2 = pid(0,32,0).
<0.32.0>
6> Pidsh2 ! hello2.
hello2
7> flush().
Shell got hello2
ok
また、 Pid3!Pid2!Pid1!Msg
を使用すると、一度に複数のプロセスにメッセージを送信することもできます。
メッセージの受信
受信したメッセージはreceive
構造で処理できます。
receive
Pattern1 -> exp11, .., exp1n1;
Pattern2 when Guard -> exp21, .., exp2n2;
...
Other -> exp31, .., exp3n3;
...
after Timeout -> exp41, .., exp4n4
end
Pattern
は、最初の最も古いメッセージから始まる「メールボックス」内のメッセージと比較されます。
パターンが一致すると、一致したメッセージが「メールボックス」から削除され、節の本文が評価されます。
また、 after
構文でタイムアウトを定義することもできます。
Timeout
は、ミリ秒単位の待ち時間またはinfinity
いずれかです。
receive
の戻り値は、最後に評価された節の本文です。
例(カウンタ)
メッセージを渡す(非常に)単純なカウンタは、次のようになります。
-module(counter0).
-export([start/0,loop/1]).
% Creating the counter process.
start() ->
spawn(counter0, loop, [0]).
% The counter loop.
loop(Val) ->
receive
increment ->
loop(Val + 1)
end.
カウンターとの相互作用。
1> C0 = counter0:start().
<0.39.0>
2> C0!increment.
increment
3> C0!increment.
increment
登録プロセス
プロセス(pid)をグローバルエイリアスに登録することは可能です。
これは、 Alias
がプロセスにアクセスするためのアトムで、 Pid
がプロセスIDであるBuild in register(Alias, Pid)
関数で実現できます。
エイリアスはグローバルに利用可能です!
共有状態を作成するのは非常に簡単ですが、通常は好ましくありません。 ( こちらもご覧ください )
unregister(Pid)
プロセスをunregister(Pid)
し、 whereis(Alias)
別名からpidを受け取ることは可能です。
registered()
すべてのエイリアスのリストは、 registered()
を使用してください。
この例では、現在のプロセスのpidにAtom fooを登録し、登録されたAtomを使用してメッセージを送信します。
1> register(foo, self()).
true
2> foo ! 'hello world'.
'hello world'