[erlang-questions] How erlang handle complicated data structure like C?

CGS cgsmcmlxxv@REDACTED
Tue Sep 20 20:26:48 CEST 2011


I agree with the illegal guard. The reason I put it that way was to cover
two cases: receive internally or via TCP connection. Your observation is
correct that such a guard doesn't work. Its sole purpose was to see the
condition. I missed your point first time and I apologize.

About the length, it depends what you prefer: slower code, but smaller, or
bigger code, but faster (I usually prefer to work with vectors even if they
are more memory consumers, but I can insert very fast search algorithms and
that is important for me at large lists). Maybe it's my style, but I start
all the time with implementing the skeleton, after that I expand it and in
the end I do optimizations. I think it's easy to guess why, so, not entering
details. Nevertheless, this is about styles of implementing things.

Cheers,
CGS





On Tue, Sep 20, 2011 at 5:00 PM, Jesper Louis Andersen <
jesper.louis.andersen@REDACTED> wrote:

> On Tue, Sep 20, 2011 at 16:13, CGS <cgsmcmlxxv@REDACTED> wrote:
> > Hi Jesper,
> >
> > Can you explain why length is a bad idea? I do not deny that matching
> left
> > and right expressions is also a solution, but I see no difference. So,
> > please, if you know a bug about length, I am interested in knowing about.
>
> length/1 is not wrong, but note that it has to traverse all of the
> list to come up with its answer. In our case, the list is fairly small
> (length/1 returns 3), so this may not matter. But for a large list,
> the call to length is going to be rather expensive. Contrast this with
> a match on the structure which is either [] or [_|_]. This match can
> be done simply by examining the head of the list. We don't have to
> traverse the list fully to get the answer.
>
> In general, a good idea is to prefer matching over calling length/1 if
> you are in doubt. It usually translates to simpler code. Another
> worthy point is that matching on lists avoids "Boolean blindness",
> which often follows due to a matching on == 3 or similar. Boolean
> Blindness is a rather deep concept, but it is worth understanding.
> See,
>
> http://existentialtype.wordpress.com/2011/03/15/boolean-blindness/
>
> The exposition could be written in a more approachable way I think,
> but I have not gotten around to doing it yet :P
>
> In a certain sense, length/1 tells us _too much_. It yields a number,
> namely the length of the list. But we are only interested in two
> limited cases, namely sizes 0 and 3. That is, length/1 can be seen as
> being too powerful for our cause.
>
> That is, there is nothing wrong with using length/1 here. You should
> just know the implications of doing so for other code pieces.
>
> >> 7. How to use the test:
> >> receive_function(Packet) when is_my_record(Packet) == true ->
> >> do_something_with_my_packet;
> >> receive_function(Packet) when is_my_record(Packet) /= true ->
> >> I_do_not_care.
> >
> > You can't do this in Erlang. Guard expressions are limited so you can
> > be sure they terminate.
> > -------------------
> >
> > Please, take a better look and you will notice I haven't used guarded
> > function for recursion, but for condition. What you said is okay for
> > recursion.
>
> The problem is shown in the following silly module:
>
> ----
> -module(f).
>
> -compile(export_all).
>
> my_own_guard(B) when is_binary(B) -> binary;
> my_own_guard(S) when is_list(S) -> list.
>
> f(X) when my_own_guard(X) == binary ->
>    binary_to_list(X);
> f(X) when my_own_guard(X) == list ->
>    X.
>
> ---
>
> When we try to compile this in the Erlang shell, it fails:
>
> Eshell V5.8.5  (abort with ^G)
> 1> c(f).
> ./f.erl:8: call to local/imported function my_own_guard/1 is illegal in
> guard
> ./f.erl:10: call to local/imported function my_own_guard/1 is illegal in
> guard
> error
> 2>
>
> The relevant part in the reference manual is the part about "Guard
> Sequences",
>
> http://www.erlang.org/doc/reference_manual/expressions.html#id78951
>
> which states exactly what subset of all expressions that are valid as
> a Guard. In particular we are only allowed to call functions in Tables
> 7.4 and 7.5 and f:my_own_guard/1 is not in that table which is why the
> above compilation fail.
>
> It is worth it to contrast this behavior with Haskell, where arbitrary
> guard sequences *are* allowed and Haskell is lazy. Or Coq, where are
> functions are total, including recursive functions. In these cases,
> termination is less of a problem.
>
> > In addition, I didn't say that was the best way to do it, but just an
> > example. Jovi needed an example and I gave. I am sorry if my code
> offended
> > you so much to call it "garbage". Feel free to propose the best working
> idea
> > for this case.
>
> Written code is never garbage if it is correct and solves the problem
> in an adequate way. Even if it contains minor errors which are not
> deep design errors, it isn't a problem - because those are quickly
> fixed. To me, that the code is there has a value in its own. This is
> mere "golfing" in the sense of producing simpler and smaller code. My
> goal was not to show the code to be bad, but rather to show an
> alternative way of implementing a solution which I do think is a bit
> more idiomatic and functional.
>
> Why? Because I think it is better you see more styles and then form an
> opinion of your own about what style you prefer when writing programs.
> In any event, consistency tends to win over smug code :) Your style
> may be easier to comprehend for a person who is more accustomed to an
> imperative code writing style. My style is, perhaps, easier for one
> with an ML or Haskell background.
>
> --
> J.
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://erlang.org/pipermail/erlang-questions/attachments/20110920/4bb170b3/attachment.htm>


More information about the erlang-questions mailing list