[erlang-questions] Trying to learn the Erlang Way

kraythe . <>
Fri Feb 7 17:45:25 CET 2014


So now the fixed code is:

%% Subtract the second vector from the first
subtract({X1, Y1, Z1}, {X2, Y2, Z2}) -> {(X1 - X2), (Y1 - Y2), (Z1 - Z2)}.

%% Compute the magnitude of the vector
magnitude({X, Y, Z}) -> math:sqrt((X * X) + (Y * Y) + (Z * Z)).

%% Compute whether the vector with components X, Y and Z has greater
magnitude then the passed scalar M.
%% Note that this method avoids the expensive sqrt operation.
is_magnitude_greater(M, {X, Y, Z}) when is_number(M), is_number(X),
is_number(Y), is_number(Z) ->
  Msq = M * M,
  Magsq = (X * X) + (Y * Y) + (Z * Z),
  Msq > Magsq.

%% Determines if any coordinate in the given vector is bigger than the
passed in value M
has_coordinate_greater_than(V, {X, Y, Z}) when X > V; Y > V; Z > V -> true;
has_coordinate_greater_than(V, Coordinate) when is_number(V),
is_tuple(Coordinate) -> false.

%% Culls the list of vectors X to only those that are in the sphere devined
by vector C as a center and R as a radius.
cull(C, R, Vectors) when is_number(R), is_tuple(C), is_list(Vectors) ->
cull(C, R, Vectors, []).
cull(C, R, [], Culled) -> Culled;
cull(C, R, [Head|Tail], Culled) ->
  D = subtract(C, Head),
  case has_coordinate_greater_than(R, Head) of
    true -> cull(C, R, Tail, Culled);
    false -> cull(C, R, D, Head, Tail, Culled)
  end.
cull(C, R, D, Head, Tail, Culled) when is_tuple(D), is_number(R) ->
  case is_magnitude_greater(R, D) of
     true -> cull(C, R, Tail, [Head | Culled]);
     false -> cull(C, R, Tail, Culled)
  end.

Now the question is the resolution of the followup question of how to
integrate this in a solution. Do we return a list of trues and falses and
zip that with the objects to form a candidate list? How would you do it?

*Robert Simmons Jr. MSc. - Lead Java Architect @ EA*
*Author of: Hardcore Java (2003) and Maintainable Java (2012)*
*LinkedIn: **http://www.linkedin.com/pub/robert-simmons/40/852/a39
<http://www.linkedin.com/pub/robert-simmons/40/852/a39>*


On Fri, Feb 7, 2014 at 9:53 AM, kraythe . <> wrote:

> Well I am not a programming newbie. ;-) Just an erlang newbie. If I had a
> dollar for every silly "is" mistake I have made, Id be rich. At any rate
> thanks for the advice. I think naming is not necessarily a religious thing,
> or it shouldn't be. It is very valid to adapt the standards of the source
> language. Thats what annoys me when people write Java code like C code.
>
> Anyway back to the subject at hand. The algorithm is set but now I am at
> another quandary Lets say these vectors represent a position in space of
> particular objects in a simulation. The process of culling the vectors
> based on the sphere is entirely a vector problem but what the user calling
> cull/3 really needs to know is which objects are not culled from the
> list, not just which vectors are not culled. Now in Java I could do a
> number of things if I wanted to keep the cull algorithm as it is. I could
> return the list of integers containing the original indexes of the vectors
> in the list that were culled and use that to filter out which objects need
> to be considered for the simulation step. I.e:
>
> List<Integer> survivors = cull(C, R, Candidates);
> for(final Integer index : survivors)
> handleSurvivor(Candidates.get(index));
>
> Now the question is what is the erlang way to do this?
>
> Thanks in advance.
>
> *Robert Simmons Jr. MSc.*
> *Author of: Hardcore Java (2003) and Maintainable Java (2012)*
> *LinkedIn: **http://www.linkedin.com/pub/robert-simmons/40/852/a39
> <http://www.linkedin.com/pub/robert-simmons/40/852/a39>*
>
>
> On Fri, Feb 7, 2014 at 9:35 AM, Garrett Smith <> wrote:
>
>> On Fri, Feb 7, 2014 at 8:47 AM, kraythe . <> wrote:
>> > Man I feel silly. but then I am fighting a chest cold. I guess this
>> happens
>> > easier when you don't have completion or highlighting that I am used to
>> in
>> > an IDE.
>>
>> Viva Eclipse!
>>
>> But seriously, every programmer knows the feeling of at once being
>> certain something's wrong with the compiler/VM and then realizing the
>> obviousness of his or her mistake. You'll pick up quickly where to
>> look for the common sources of these.
>>
>> Fred's comments on function naming are spot on - lower camel case is
>> almost never ever seen in Erlang and really stands out in a bad and
>> distracting way. I know this sounds religious, and it is, but it's the
>> True Religion, so it's fine.
>>
>> Having very, very focused functions helps a lot both in writing a
>> program (it forces the programmer to make things obvious in code,
>> which is very hard to do but an excellent way to prove you understand
>> exactly what problems you're solving) and to debug a program (it's
>> hard for problems to lurk in obvious code).
>>
>> This blog post says what I mean:
>>
>>
>> http://www.gar1t.com/blog/solving-embarrassingly-obvious-problems-in-erlang.html
>>
>> It's also True Religion, so it's fine. [1]
>>
>> In cases where you really need to step through code (I think these are
>> rare, especially if you follow the obviousness rule) the function
>> tracing tools in Erlang are fantastic. Reid Draper happened to have
>> just presented a great tracing tool called redbug at the Chicago
>> Erlang User Group this Wednesday:
>>
>> https://github.com/massemanet/eper/blob/master/src/redbug.erl
>>
>> I've historically used e2's e2_debug module:
>>
>> https://github.com/gar1t/e2/blob/master/src/e2_debug.erl
>>
>> I'll might switch to redbug because it stops tracing automatically
>> after a period of time or number of traces, which is super great for
>> use in production systems. e2_debug is fine for local dev however --
>> and it's output is IMO much easier to read.
>>
>> While you can use the Erlang visual debugger to step through code, I
>> personally find this time consuming and awkward and prefer to trace.
>> Problems in Erlang often come down to unexpected patterns that sneak
>> into a call chain, which are easy to spot through tracing.
>>
>> Best of luck!
>>
>> Garrett
>>
>> [1] There is one stylistic change that I would recommend, vis-a-vis
>> that blog post, which is to *selectively* use variables to pull
>> important, side effecty operations out of nested function calls so
>> that they appear earlier in the function (western style top-down,
>> left-right reading) and get named results (via variable binding). So,
>> e.g.
>>
>>     do_something_next(do_something_first())
>>
>> Becomes:
>>
>>    FirstResult = do_something_first()
>>    do_something_next(FirstResult)
>>
>> God names are essential - these are terrible names, but you get the idea.
>>
>> Do this only when it makes the code more obvious.
>>
>> Richard O'Keefe pointed this out to me originally and, of course, he's
>> right.
>>
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://erlang.org/pipermail/erlang-questions/attachments/20140207/8a513bd8/attachment.html>


More information about the erlang-questions mailing list