[erlang-questions] Nested for-loops, there has to be a better way to do this
Brentley Jones
the.ajarn@REDACTED
Wed Jul 29 20:12:12 CEST 2009
This is my take on it:
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-module(for).
-export([for/4, test_1/0, test_2/0]).
for(BodyFun, Acc, ConditionFun, StepFun) ->
Done = ConditionFun(Acc),
if Done == false ->
Acc;
true ->
NewAcc = BodyFun(Acc),
LastAcc = StepFun(NewAcc),
for(BodyFun, LastAcc, ConditionFun, StepFun)
end.
test_1() ->
Body = fun(I) ->
io:format("i=~p~n", [I]),
I
end,
for(Body, 0, fun(I) -> I < 10 end, fun(I) -> I + 1 end),
ok.
test_2() ->
CondFun = fun(X) -> X < 5 end,
StepFun = fun(X) -> X + 1 end,
BodyInner = fun(J) ->
io:format("~p", [J]),
J
end,
BodyOuter = fun(I) ->
for(BodyInner, 0, CondFun, StepFun),
io:format("~n"),
I
end,
for(BodyOuter, 0, CondFun, StepFun),
ok.
%%%%% Output:
2> for:test_2().
01234
01234
01234
01234
01234
ok
3> for:test_1().
i=0
i=1
i=2
i=3
i=4
i=5
i=6
i=7
i=8
i=9
ok
On Jul 29, 2009, at 11:25 AM, Cláudio Amaral wrote:
> Used some of previous code...
>
> I tried to make a polymorphic function and coupled an example...
> this ended a little bit confusing, but as you can see, it makes all
> iterations (check the printed indexes, reversed).
>
> The body behaviour is the tricky stuff to code, but in exchange it
> is modular...
>
> Since I am an erlang newb, please correct anything you see as bad
> programming
>
> Cláudio
>
> %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
> -module(for_loop).
>
> -export([for/4, show/0]).
>
>
> for(BodyFunc, BodyArgs, StepFunc, {First, Last}) ->
> for_(BodyFunc, BodyArgs, StepFunc, {First, Last}, First).
>
>
> for_(BodyFunc, BodyArgs, StepFunc, {_, LastTerm}, LastTerm) ->
> BodyFunc(BodyArgs, LastTerm);
> for_(BodyFunc, BodyArgs, StepFunc, LimitsTuple, IndexTerm) ->
> NextArgs = BodyFunc(BodyArgs, IndexTerm),
> for_(BodyFunc, NextArgs, StepFunc, LimitsTuple,
> StepFunc(IndexTerm)).
>
>
> show() ->
> for( fun(A1,A2)->body1(A1,A2) end,
> [{0,3}, [{1,0}], [{3,6},{1,2}]],
> fun(I) -> I+1 end,
> {0,3}
> ).
>
>
> body1([ LimitsTuple, [{NLoop,II}|Rest], []],I) ->
> print([ I | lists:map(fun({_,Snd}) -> Snd end, Rest) ]),
> IndexInfo = [{NLoop,II}|Rest],
> [ LimitsTuple, IndexInfo, []];
> body1([ LimitsTuple, [{NLoop,II}|Rest], [{X1,Xn}|XS]],I) ->
> for( fun (A1,A2)->body1(A1,A2) end,
> [ LimitsTuple, [ {NLoop+1,II}, {NLoop,I} | Rest ], XS],
> fun(K) -> K+1 end,
> {X1,Xn}
> ),
> IndexInfo = [{NLoop,II}|Rest],
> [ LimitsTuple, IndexInfo, [{X1,Xn}|XS] ].
>
> print(Numbers) ->
> io:format("indexes ~p~n", [Numbers]).
>
>
> kiszl@REDACTED escreveu:
>> Regards,
>> Z.
>>
>>
>>> I was playing around with the idea of implementing a nested for-loop
>>> like construct (I will concede, they are evil, but at rare times,
>>> necessary.) In non-functional programming languages, they are
>>> trivial
>>> to do. However, this has proved to be one of those simple things
>>> that
>>> are a pain in the neck for me. The idea was to be able to pass in a
>>> list [5, 5, 10] (for example) and go through it all like 3
>>> dimensional
>>> array. The below illustration is far from elegant (it's almost
>>> 23:00
>>> where I live and need to go to work tomorrow early, so no time to
>>> come
>>> up with something more sane :) ), but is there as an inquisitive
>>> exercise. Now, in my opinion, this implementation sucks (first time
>>> I've ever gave such a problem a shot in Erlang.)
>>>
>>> Is there a better way to do this? Anyone would like to demonstrate
>>> it?
>>>
>>> Note: I've tested this code with the lists [2, 4] and [2, 4, 5].
>>>
>>> Compiled with:
>>> Erlang (SMP,ASYNC_THREADS,HIPE) (BEAM) emulator version 5.6.5
>>>
>>> My code:
>>> ======================================
>>> -module(loopWrapper).
>>>
>>> -export([runLoop/1]).
>>>
>>> runLoop(List) ->
>>> [FirstVal | RestList] = List,
>>> NextVal = FirstVal - 1,
>>> if (length(RestList) > 0) and (FirstVal > 0) ->
>>> io:format("~B~n~n", [FirstVal]),
>>> runLoop(RestList),
>>> io:format("~n~n"),
>>> runLoop([NextVal | RestList]);
>>> FirstVal > 0 ->
>>> io:format("~B", [FirstVal]),
>>> runLoop([NextVal]);
>>> true ->
>>> null
>>> end.
>>>
>>> ________________________________________________________________
>>> erlang-questions mailing list. See http://www.erlang.org/faq.html
>>> erlang-questions (at) erlang.org
>>>
>>>
>>>
>>
>>
>>
>> ________________________________________________________________
>> erlang-questions mailing list. See http://www.erlang.org/faq.html
>> erlang-questions (at) erlang.org
>>
>>
>
>
> ________________________________________________________________
> erlang-questions mailing list. See http://www.erlang.org/faq.html
> erlang-questions (at) erlang.org
>
More information about the erlang-questions
mailing list