Skip to content

Commit

Permalink
Get a match function working.
Browse files Browse the repository at this point in the history
  • Loading branch information
Samuel Tesla committed Jul 16, 2009
1 parent 2cb8a53 commit 0655bdd
Show file tree
Hide file tree
Showing 2 changed files with 40 additions and 6 deletions.
22 changes: 18 additions & 4 deletions src/matcher.erl
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
-behaviour(gen_server).

%% API
-export([add_sequence/1, start_link/0]).
-export([add/1, match/2, start_link/0]).

%% gen_server callbacks
-export([init/1, handle_call/3, handle_cast/2, handle_info/2,
Expand All @@ -24,8 +24,11 @@
start_link() ->
gen_server:start_link({local, ?SERVER}, ?MODULE, [], []).

add_sequence(Seq) ->
gen_server:call(?SERVER, {add_sequence, Seq}).
add(Seq) ->
gen_server:call(?SERVER, {add, Seq}).

match(Seq, Degree) ->
gen_server:call(?SERVER, {match, Seq, Degree}).

%%====================================================================
%% gen_server callbacks
Expand All @@ -51,12 +54,23 @@ init([]) ->
%% {stop, Reason, State}
%% Description: Handling call messages
%%--------------------------------------------------------------------
handle_call({add_sequence, Seq}, _From, State) ->
handle_call({add, Seq}, _From, State) ->
%% TODO: Remove magic numbers.
L1 = mg_util:combinations(Seq, 1),
L2 = mg_util:combinations(Seq, 2),
Reply = ets:insert(?TABLE, [{X, Seq} || X <- L1++L2]),
{reply, Reply, State};

handle_call({match, Seq, Degree}, _From, State) ->
Cs = mg_util:combinations(Seq, Degree),
Ms = lists:foldl(fun(C, Acc) ->
ets:lookup(?TABLE, C) ++ Acc
end, [], Cs),
Reply = length(lists:filter(fun(Elt) ->
mg_util:is_mutation(Seq, Elt)
end, Ms)),
{reply, Reply, State};

handle_call(_Request, _From, State) ->
Reply = ok,
{reply, Reply, State}.
Expand Down
24 changes: 22 additions & 2 deletions src/mg_util.erl
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
-module(mg_util).

-export([combinations/2]).
-export([combinations/2, is_mutation/2]).

-define(POINT, $$).

combinations(Seq, Degree) when Degree > 1 ->
L = lists:foldr(fun (Elt, Acc) -> combinations(Elt, 1) ++ Acc end,
Expand All @@ -11,9 +13,27 @@ combinations(Seq, 1) ->
F = fun (Pos, Acc) ->
Head = lists:sublist(Seq, Pos - 1),
Tail = lists:nthtail(Pos, Seq),
[Head ++ "$" ++ Tail | Acc]
[Head ++ [?POINT] ++ Tail | Acc]
end,
lists:filter(fun(X) when X =:= Seq -> false;
(_) -> true
end,
lists:foldr(F, [], lists:seq(1, length(Seq)))).

is_mutation(Seq1, {_, Seq2}) when Seq1 =:= Seq2 ->
false;
is_mutation(Seq1, {_, Seq2}) when length(Seq1) =/= length(Seq2) ->
false;
is_mutation(Seq1, {Key, Seq2}) ->
only_differs_at_points(Seq1, Key, Seq2).

only_differs_at_points([], [], []) ->
true;
only_differs_at_points([C|_], [?POINT|_], [C|_]) ->
false;
only_differs_at_points([_|As], [?POINT|Ks], [_|Bs]) ->
only_differs_at_points(As, Ks, Bs);
only_differs_at_points([C|As], [_|Ks], [C|Bs]) ->
only_differs_at_points(As, Ks, Bs);
only_differs_at_points(_,_,_) ->
false.

0 comments on commit 0655bdd

Please sign in to comment.