Anonymous user
Checkpoint synchronization: Difference between revisions
no edit summary
m (Take task description off of the TOC) |
No edit summary |
||
Line 14:
=={{header|Ada}}==
<lang Ada>with Ada.Calendar; use Ada.Calendar;
with
with Ada.Text_IO; use Ada.Text_IO;
procedure Test_Checkpoint is
package FR renames Ada.Numerics.Float_Random;
No_Of_Cubicles: constant Positive := 3;
-- That many workers can work in parallel
No_Of_Workers: constant Positive := 6;
-- That many workers are potentially available
-- some will join the team when others quit the job
type Activity_Array is array(Character) of Boolean;
-- we want to know who is currently working
protected Checkpoint is
entry Deliver;
entry Join (Label : out Character; Tolerance: out Float);
entry Leave(Label : in Character);
private
Signaling : Boolean := False;
Ready_Count : Natural := 0;
Worker_Count : Natural := 0;
Unused_Label : Character := 'A';
Likelyhood_To_Quit: Float := 1.0;
Active : Activity_Array := (others => false);
entry Lodge;
end Checkpoint;
protected body Checkpoint is
entry Join (Label : out Character
when not Signaling and Worker_Count < No_Of_Cubicles is
begin
Label := Unused_Label;
Active(Label):= True;
Unused_Label := Character'Succ (Unused_Label);
Worker_Count := Worker_Count + 1;
Likelyhood_To_Quit := Likelyhood_To_Quit / 2.0;
Tolerance := Likelyhood_To_Quit;
end Join;
entry Leave(Label: in Character) when not Signaling is
begin
Worker_Count := Worker_Count - 1;
Active(Label) := False;
end Leave;
Line 51 ⟶ 69:
entry Lodge when Ready_Count = Worker_Count or Signaling is
begin
if Ready_Count = Worker_Count then
Put("---Sync Point [");
for C in Character loop
if Active(C) then
Put(C);
end if;
end loop;
Put_Line("]---");
end if;
Ready_Count := Ready_Count - 1;
Signaling := Ready_Count /= 0;
end Lodge;
end Checkpoint;
task type Worker;
task body Worker is
Dice : FR.Generator;
Label : Character;
Tolerance : Float;
Shift_End : Time := Clock + 2.0;
-- Trade unions are hard!
begin
FR.Reset (Dice);
Checkpoint.Join (Label, Tolerance);
Put_Line(Label & " joins the team");
loop
Put_Line (Label & " is working");
delay Duration (FR.Random (Dice) * 0.
Put_Line (Label & " is ready");
Checkpoint.Deliver;
Put_Line(Label & " leaves the team");
exit;
elsif Clock >= Shift_End then
Put_Line(Label & " ends shift");
exit;
end if;
end loop;
Checkpoint.Leave(Label);
end Worker;
Set : array (1..No_Of_Workers) of Worker;
begin
null; -- Nothing to do here
end Test_Checkpoint;
</lang>
Sample output:
<pre style="height: 200px;overflow:scroll">
A joins the team
A is working
B joins the team
B is working
C joins the team
C is working
B is ready
C is ready
A is ready
---Sync Point [ABC]---
A is working
C is working
B is working
B is ready
A is ready
---Sync Point [ABC]---
A is working
B is working
C is working
B is ready
C is ready
A is ready
---Sync Point [ABC]---
A leaves the team
D joins the team
D is working
C is working
B is working
C is ready
B is ready
D is ready
---Sync Point [BCD]---
D is working
C is working
B is working
C is ready
B is ready
D is ready
---Sync Point [BCD]---
D is working
C is working
B is working
D is ready
B is ready
C is ready
---Sync Point [BCD]---
C leaves the team
E joins the team
D is working
B leaves the team
F joins the team
F is working
D is ready
---Sync Point [DEF]---
D is working
D is ready
---Sync Point [DEF]---
E ends shift
F ends shift
D ends shift
</pre>
=={{header|E}}==
|