Skip to content

Instantly share code, notes, and snippets.

@hamidreza-s
Last active August 29, 2015 14:16
Show Gist options
  • Save hamidreza-s/78c8b3a7a997821bd234 to your computer and use it in GitHub Desktop.
Save hamidreza-s/78c8b3a7a997821bd234 to your computer and use it in GitHub Desktop.
An Erlang module for counting a word occurrence inside a given directory files.
%% part 1: utility module
%% ======================
-module(utility).
-export([count/2]).
%% part 2: count function
%% ======================
count(Dir, Word) ->
Accumulator = 0,
CounterPid = spawn(fun() -> counter(Accumulator) end),
register(counter, CounterPid),
count_on_dir(Dir, Word).
%% part 3: counter function
%% ========================
counter(Accumulator) ->
receive
stat -> io:format("~p~n", [Accumulator]), counter(Accumulator);
exit -> io:format("~p~n", [Accumulator]);
Count -> counter(Accumulator + Count)
end.
%% part 4: count_on_dir function
%% =============================
count_on_dir(Dir, Word) ->
Files = list_files(Dir),
count_on_files(Files, Word).
%% part 5: count_on_files function
%% ===============================
count_on_files([File|RestFiles], Word) ->
spawn(fun() -> do_count(File, Word) end),
count_on_files(RestFiles, Word);
count_on_files([], _Word) -> ok.
%% part 6: do_count function
%% =========================
do_count(File, Word) ->
{ok, OpenFile} = file:open(File, read),
read_file(OpenFile, Word).
%% part 7: read_file function
%% ==========================
read_file(OpenFile, Word) ->
case io:get_line(OpenFile, "") of
eof -> file:close(OpenFile);
Line ->
read_line(Line, Word),
read_file(OpenFile, Word)
end.
%% part 8: read_line function
%% ==========================
read_line(Line, Word) ->
case re:run(Line, Word, [global]) of
{match, MatchedList} -> counter ! length(MatchedList);
_ -> ok
end.
%% part 9: list_files function
%% ===========================
list_files(Dir) ->
{ok, Files} = file:list_dir(Dir),
FilterMap = fun(FileName) ->
FilePath = Dir ++ "/" ++ FileName,
case filelib:is_dir(FilePath) of
true -> false;
false -> {true, FilePath}
end
end,
lists:filtermap(FilterMap, Files).
$ erl
Eshell V5.10.4 (abort with ^G)
1> c(utility).
2> utility:count("/your/dir", "salam_donya").
3> counter ! stat.
4> counter ! exit.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment