From 5a9cdd3cc89507d4d74f8bded56ce5e037b3b56e Mon Sep 17 00:00:00 2001 From: Trygve Laugstøl Date: Fri, 23 Feb 2024 07:08:18 +0100 Subject: wip --- learn-you-some-erlang/musicians.erl | 84 +++++++++++++++++++++++++++++++++++++ 1 file changed, 84 insertions(+) create mode 100644 learn-you-some-erlang/musicians.erl (limited to 'learn-you-some-erlang/musicians.erl') diff --git a/learn-you-some-erlang/musicians.erl b/learn-you-some-erlang/musicians.erl new file mode 100644 index 0000000..e369d44 --- /dev/null +++ b/learn-you-some-erlang/musicians.erl @@ -0,0 +1,84 @@ +-module(musicians). +-behaviour(gen_server). + +-export([start_link/2, stop/1]). +-export([init/1, handle_call/3, handle_cast/2, + handle_info/2, code_change/3, terminate/2]). + +-record(state, {name="", role, skill=good}). +-define(DELAY, 750). + +start_link(Role, Skill) -> + gen_server:start_link({local, Role}, ?MODULE, [Role, Skill], []). + +stop(Role) -> gen_server:call(Role, stop). + +init([Role, Skill]) -> + %% To know when the parent shuts down + process_flag(trap_exit, true), + %% sets a seed for random number generation for the life of the process + %% uses the current time to do it. Unique value guaranteed by now() + random:seed(now()), + TimeToPlay = random:uniform(3000), + Name = pick_name(), + StrRole = atom_to_list(Role), + io:format("Musician ~s, playing the ~s entered the room~n", + [Name, StrRole]), + {ok, #state{name=Name, role=StrRole, skill=Skill}, TimeToPlay}. + +handle_call(stop, _From, S=#state{}) -> + {stop, normal, ok, S}; +handle_call(_Message, _From, S) -> + {noreply, S, ?DELAY}. + +handle_cast(_Message, S) -> + {noreply, S, ?DELAY}. + +handle_info(timeout, S = #state{name=N, skill=good}) -> + io:format("~s produced sound!~n",[N]), + {noreply, S, ?DELAY}; +handle_info(timeout, S = #state{name=N, skill=bad}) -> + case random:uniform(5) of + 1 -> + io:format("~s played a false note. Uh oh~n",[N]), + {stop, bad_note, S}; + _ -> + io:format("~s produced sound!~n",[N]), + {noreply, S, ?DELAY} + end; +handle_info(_Message, S) -> + {noreply, S, ?DELAY}. + +code_change(_OldVsn, State, _Extra) -> + {ok, State}. + +terminate(normal, S) -> + io:format("~s left the room (~s)~n",[S#state.name, S#state.role]); +terminate(bad_note, S) -> + io:format("~s sucks! kicked that member out of the band! (~s)~n", + [S#state.name, S#state.role]); +terminate(shutdown, S) -> + io:format("The manager is mad and fired the whole band! " + "~s just got back to playing in the subway~n", + [S#state.name]); +terminate(_Reason, S) -> + io:format("~s has been kicked out (~s)~n", [S#state.name, S#state.role]). + +%% Yes, the names are based off the magic school bus characters +%% 10 names! +pick_name() -> + %% the seed must be set for the random functions. Use within the + %% process that started with init/1 + lists:nth(random:uniform(10), firstnames()) + ++ " " ++ + lists:nth(random:uniform(10), lastnames()). + +firstnames() -> + ["Valerie", "Arnold", "Carlos", "Dorothy", "Keesha", + "Phoebe", "Ralphie", "Tim", "Wanda", "Janet"]. + +lastnames() -> + ["Frizzle", "Perlstein", "Ramon", "Ann", "Franklin", + "Terese", "Tennelli", "Jamal", "Li", "Perlstein"]. + + -- cgit v1.2.3