Wie der letzte Rückgabewert aufgebaut ist ...
Wenn [Msg | important()]
zum ersten Mal zurückgegeben wird, wird die Form des endgültigen Rückgabewert bestimmt wird. Die einzige Sorge ist, dass wir noch nicht alle Details des endgültigen Rückgabewerts kennen. So wird die important()
in der [Msg | important()]
weiterhin ausgewertet werden. Die folgende Abbildung zeigt, wie der endgültige Rückgabewert [high,high,low,low]
erstellt wird.
[high | important( )] <---- Defines the final form
---------------------------------
[high | important( )] <---- Adds more details
------------------------
normal( ) <---- Adds more details
------------------------
[low | normal( )] <---- Adds more details
----------------
[low | normal()] <---- Adds more details
--------
[ ] <---- Adds more details
------------------------------------------
[high | [high | [low | [low | []]]]]
[high,high,low,low] <---- The final return value
Wie der Code funktioniert ...
In Funktion important/0
bedeutet after 0
einfach: „Ich warte nicht auf Nachrichten kommen“ - wenn es eine Nachricht in meinem Briefkasten, ich werde es anschauen; Wenn es keine gibt, werde ich weitermachen (execute normal()
), anstatt dort zu warten.Im Postfach befinden sich {15, hoch}, {7, niedrig}, {1, niedrig}, {17, hoch} sitzen dort schon. In Erlang sind die Nachrichten in der Mailbox Nicht in der Reihenfolge der Reihenfolge, in der sie zuerst eingehen. Die Klausel receive
kann wählerisch sein. Es durchsucht alle Nachrichten in der Mailbox und "wählt" die gewünschten aus. In unserem Fall werden {15, hoch} und {17, hoch} zuerst nach {Priority, Msg} when Priority > 10
ausgewählt werden. Danach übernimmt die Funktion normal/0
. Und {7, niedrig}, {1, niedrig} werden verarbeitet (consed) in der Reihenfolge. Schließlich haben wir [high,high,low,low]
.
Eine modifizierte Version, die die Verarbeitungsreihenfolge enthüllt ...
wir den Code ein wenig modifizieren, kann die Verarbeitung (consing), um deutlicher zu machen:
-module(prior).
-compile(export_all).
important() ->
receive
{Priority, Msg} when Priority > 10 ->
[{Priority, Msg} | important()] % <---- Edited
after 0 ->
normal()
end.
normal() ->
receive
{Priority, Msg} -> % <---- Edited
[{Priority, Msg} | normal()] % <---- Edited
after 0 ->
[]
end.
Run es in der Schale:
4> c(prior).
{ok, prior}
5> self() ! {15, high}, self() ! {7, low}, self() ! {1, low}, self() ! {17, high}.
{17,high}
6> prior:important().
[{15,high},{17,high},{7,low},{1,low}]
Nicht verkettet, consed. Verkettung ist, wenn Sie zwei Listen haben, "L1" und "L2" und verketten Sie sie: "L1 ++ L2". Consing ist, wenn Sie ein Element 'E' und eine Liste' L' haben und dann die erweiterte Liste '[E | bilden L] '. –