I did profile these two methods out of curiosity, and it looks like
list comp is 2x faster -- but that's 2x faster than a very, very, very
small number so I wouldn't use that as a gauge.
It seems like these usually accomplish the same task. Is there an
advantage to one over the other?
-module(test).
-export([run/0]).
run() ->
Seq = lists:seq(1,1000000),
comp(10, Seq),
mapper(10, Seq).
mapper(0, _Seq) ->
ok;
mapper(Iter, Seq) ->
Now1 = now(),
Res = lists:map(fun(N) -> N + 1 end, Seq),
Now2 = now(),
self() ! hd(Res),
io:format("Map time: ~p~n", [timer:now_diff(Now2, Now1)]),
mapper(Iter - 1, Seq).
comp(0, _Seq) ->
ok;
comp(Iter, Seq) ->
Now1 = now(),
Res = [N + 1 || N <- Seq],
Now2 = now(),
self() ! hd(Res),
io:format("Comprehension time: ~p~n", [timer:now_diff(Now2, Now1)]),
comp(Iter - 1, Seq).
and here are the results
1> test:run().
Comprehension time: 96650
Comprehension time: 28795
Comprehension time: 30056
Comprehension time: 28711
Comprehension time: 29349
Comprehension time: 28781
Comprehension time: 29186
Comprehension time: 28917
Comprehension time: 30079
Comprehension time: 28814
Map time: 56983
Map time: 57545
Map time: 57082
Map time: 57151
Map time: 57469
Map time: 56867
Map time: 57706
Map time: 57467
Map time: 57088
Map time: 57701
ok
The comprehension in this case is about twice as fast as the higher
order function.
Cheers,
Martin
-module(test).
-export([run/0]).
run() ->
Seq = lists:seq(1,1000000),
comp(10, Seq),
mapper(10, Seq).
mapper(0, _Seq) ->
ok;
mapper(Iter, Seq) ->
Now1 = now(),
lists:map(fun(N) -> N + 1 end, Seq),
Now2 = now(),
io:format("Map time: ~p~n", [timer:now_diff(Now2, Now1)]),
mapper(Iter - 1, Seq).
comp(0, _Seq) ->
ok;
comp(Iter, Seq) ->
Now1 = now(),
[N + 1 || N <- Seq],
Now2 = now(),
io:format("Comprehension time: ~p~n", [timer:now_diff(Now2, Now1)]),
comp(Iter - 1, Seq).
1> test:run().
Comprehension time: 10786
Comprehension time: 10869
Comprehension time: 10869
Comprehension time: 10849
Comprehension time: 10931
Comprehension time: 10952
Comprehension time: 10888
Comprehension time: 10857
Comprehension time: 11230
Comprehension time: 10967
Map time: 112854
Map time: 141781
Map time: 57468
Map time: 57838
Map time: 57732
Map time: 58423
Map time: 57160
Map time: 58190
Map time: 57134
Map time: 57663
ok
If I get rid of the assignment of the value for the list comprehension
and the actual use of that variable then I speed the time of the
comprehension up considerably. In fact, the use never even mattered,
the compiler seems only to check if there is an assignment of the
value of the list comprehension when deciding how to optimize.
Cheers,
Martin