Data commit
This commit is contained in:
parent
7387c8f97b
commit
cb5bb5e222
199093 changed files with 3378972 additions and 0 deletions
88
Task/Atomic-updates/Erlang/atomic-updates.erl
Normal file
88
Task/Atomic-updates/Erlang/atomic-updates.erl
Normal file
|
|
@ -0,0 +1,88 @@
|
|||
-module( atomic_updates ).
|
||||
-export( [buckets/1, buckets_get/2, buckets_get_all/1, buckets_move_contents/4, task/0] ).
|
||||
|
||||
buckets( N ) ->
|
||||
Buckets = erlang:list_to_tuple( lists:seq(1, N) ),
|
||||
erlang:spawn_link( fun() -> buckets_loop(Buckets) end ).
|
||||
|
||||
buckets_get( N, Buckets_pid ) ->
|
||||
{is_buckets_alive, true} = {is_buckets_alive, erlang:is_process_alive( Buckets_pid )},
|
||||
Buckets_pid ! {get, N, erlang:self()},
|
||||
receive
|
||||
{value, Buckets_pid, Value} -> Value
|
||||
end.
|
||||
|
||||
buckets_get_all( Buckets_pid ) ->
|
||||
{is_buckets_alive, true} = {is_buckets_alive, erlang:is_process_alive( Buckets_pid )},
|
||||
Buckets_pid ! {get_all, erlang:self()},
|
||||
receive
|
||||
{values, Buckets_pid, Values} -> Values
|
||||
end.
|
||||
|
||||
buckets_move_contents( Amount, From, To, Buckets_pid ) ->
|
||||
{is_buckets_alive, true} = {is_buckets_alive, erlang:is_process_alive( Buckets_pid )},
|
||||
Buckets_pid ! {move_contents, Amount, From, To, erlang:self()},
|
||||
receive
|
||||
{move_contents_done, Buckets_pid} -> ok
|
||||
end.
|
||||
|
||||
task() ->
|
||||
erlang:spawn( fun() ->
|
||||
N = 10,
|
||||
Buckets = buckets( N ),
|
||||
erlang:spawn_link( fun() -> closer_loop(N, Buckets) end ),
|
||||
erlang:spawn_link( fun() -> redistribute_loop(N, Buckets) end ),
|
||||
display_loop( 0, N, Buckets ),
|
||||
erlang:exit( stop )
|
||||
end ).
|
||||
|
||||
|
||||
|
||||
closer_loop( N, Buckets ) ->
|
||||
One = random:uniform( N ),
|
||||
Two = random:uniform( N ),
|
||||
Difference = buckets_get( One, Buckets ) - buckets_get( Two, Buckets ),
|
||||
{Amount, From, To} = closer_loop_how_to_move( Difference, One, Two ),
|
||||
buckets_move_contents( Amount, From, To, Buckets ),
|
||||
closer_loop( N, Buckets ).
|
||||
|
||||
closer_loop_how_to_move( Difference, One, Two ) when Difference < 0 ->
|
||||
{-1* Difference div 2, Two, One};
|
||||
closer_loop_how_to_move( Difference, One, Two ) ->
|
||||
{Difference div 2, One, Two}.
|
||||
|
||||
buckets_loop( Buckets ) ->
|
||||
receive
|
||||
{get, N, Pid} ->
|
||||
Pid ! {value, erlang:self(), erlang:element( N, Buckets )},
|
||||
buckets_loop( Buckets );
|
||||
{get_all, Pid} ->
|
||||
Pid ! {values, erlang:self(), erlang:tuple_to_list( Buckets )},
|
||||
buckets_loop( Buckets );
|
||||
{move_contents, Amount, From, To, Pid} ->
|
||||
Pid ! {move_contents_done, erlang:self()},
|
||||
buckets_loop( buckets_loop_move_contents(Amount, From, To, Buckets) )
|
||||
end.
|
||||
|
||||
buckets_loop_move_contents( _Amount, Same, Same, Buckets ) ->
|
||||
Buckets;
|
||||
buckets_loop_move_contents( Amount, From, To, Buckets ) ->
|
||||
Amount_from = erlang:element( From, Buckets ),
|
||||
Clamped_amount = erlang:min( Amount, Amount_from ),
|
||||
Removed = erlang:setelement( From, Buckets, Amount_from - Clamped_amount ),
|
||||
Amount_to = erlang:element( To, Buckets ) + Clamped_amount,
|
||||
erlang:setelement( To, Removed, Amount_to ).
|
||||
|
||||
display_loop( N, N, _Buckets ) -> ok;
|
||||
display_loop( Counter, N, Buckets ) ->
|
||||
Contents = buckets_get_all( Buckets ),
|
||||
io:fwrite( "~p = ~p~n", [Contents, lists:sum(Contents)] ),
|
||||
timer:sleep( 100 ),
|
||||
display_loop( Counter + 1, N, Buckets ).
|
||||
|
||||
redistribute_loop( N, Buckets ) ->
|
||||
Amount = random:uniform( N ),
|
||||
From = random:uniform( N ),
|
||||
To = random:uniform( N ),
|
||||
buckets_move_contents( Amount, From, To, Buckets ),
|
||||
redistribute_loop( N, Buckets ).
|
||||
Loading…
Add table
Add a link
Reference in a new issue