[erlang-questions] fprof overestimate the cost of list comprehension ?

Zhongzheng Liu <>
Tue Jul 5 04:31:34 CEST 2016


Hi mail list:

I profiled my program and found the performance of tail recursion and
reverse is always better than list comprehension in fprof. I feel strange
after reading the discuss in mail list <
http://erlang.org/pipermail/erlang-questions/2016-June/089479.html> and
wrote a small test myself.

The result showed that list comprehension run faster in timer:tc/3, but
slower in fprof.

I think the result of timer:tc/3 is more believable and fprof is
overestimate the cost of list comprehension. This will be misleading when I
do performance optimization guided by fprof.

Why it happens and how to correct the result of fprof?


Best
                    Liu Zhongzheng

=======================================
6> timer:tc(tst, repeat_tail_recu, [10000000]).
{4165000,ok}
7> timer:tc(tst, repeat_list_comp, [10000000]).
{3713000,ok}


=======================================
1> fprof:apply(tst, compare, [10000]).
ok
2> fprof:profile().
Reading trace data...
End of trace!
ok
3> fprof:analyse().
%                                               CNT       ACC       OWN

[{ totals,                                     470633,  875.885,
 860.659}].  %%%

{[{{error_handler,undefined_function,3},          1,  860.879,    0.003},

  {{tst,compare,1},                            10000,    0.000,   35.380}],

 { {tst,compare,1},                            10001,  860.879,   35.383},
    %
 [{{tst,list_comp,1},                          10000,  457.673,   10.006},

  {{tst,tail_recu,1},                          10000,  367.803,   10.005},

  {suspend,                                      20,    0.020,    0.000},

  {{tst,compare,1},                            10000,    0.000,
35.380}]}.


=======================================
Here is my test code.


%% tst.erl
-module(tst).
-compile([export_all]).

list_comp(L) ->
    [sq(I) || I <- L].

tail_recu(L) ->
    tail_recu(L, []).

tail_recu([H|T], Acc) ->
    tail_recu(T, [sq(H)|Acc]);
tail_recu([], Acc) ->
    lists:reverse(Acc).

sq(X) ->
    X*X.

compare(0) ->
    ok;
compare(N) ->
    L = [1,2,3,4,5,6,7,8,9,10],
    list_comp(L),
    tail_recu(L),
    compare(N-1).

repeat_list_comp(0) ->
    ok;
repeat_list_comp(N) ->
    L = [1,2,3,4,5,6,7,8,9,10],
    list_comp(L),
    repeat_list_comp(N-1).

repeat_tail_recu(0) ->
    ok;
repeat_tail_recu(N) ->
    L = [1,2,3,4,5,6,7,8,9,10],
    tail_recu(L),
    repeat_tail_recu(N-1).

% eof
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://erlang.org/pipermail/erlang-questions/attachments/20160705/39f3bea9/attachment.html>


More information about the erlang-questions mailing list