Matching Empty maps

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
7 messages Options
Reply | Threaded
Open this post in threaded view
|

Matching Empty maps

Joe Armstrong-2
Ten minutes ago I was happily recursing down a list and discovered
to my horror that an empty map isn't an empty map.

1> #{} = #{a => 1}.
#{a => 1}

The documentation actually says:

<quote>
#{} = Expr

This expression matches if the expression Expr is of type map,
otherwise it fails with an exception badmatch.
</quote>

So #{} is an empty map in an argument position but not an empty map
in a pattern.

So this is not a bug since the system does what the documentation says
but it is very weird.

Is there some deep reason for this that I've missed ??????

Very Puzzled

/Joe
_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
Reply | Threaded
Open this post in threaded view
|

Re: Matching Empty maps

Dmytro Lytovchenko
Trying to have a comfortable syntax brings all sorts of special cases not covered. One should use == or =:= in a guard, or true = (X == #{}) which is ugly.

2017-02-07 12:45 GMT+01:00 Joe Armstrong <[hidden email]>:
Ten minutes ago I was happily recursing down a list and discovered
to my horror that an empty map isn't an empty map.

1> #{} = #{a => 1}.
#{a => 1}

The documentation actually says:

<quote>
#{} = Expr

This expression matches if the expression Expr is of type map,
otherwise it fails with an exception badmatch.
</quote>

So #{} is an empty map in an argument position but not an empty map
in a pattern.

So this is not a bug since the system does what the documentation says
but it is very weird.

Is there some deep reason for this that I've missed ??????

Very Puzzled

/Joe
_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions


_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
Reply | Threaded
Open this post in threaded view
|

Re: Matching Empty maps

zxq9-2
In reply to this post by Joe Armstrong-2
On 2017年2月7日 火曜日 12:45:15 Joe Armstrong wrote:
> Is there some deep reason for this that I've missed ??????

A few places exist where slick syntax is mistaken for actual values.
That always leads to a weird place.

That is one reason that I generally avoid using the special map syntax
over the functional interface to maps with the exception of explicit
unification matches. (Which still can't do everything I wish they
could, but I assume that is coming since everyone feels the same way
about that stuff.)

-Craig
_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
Reply | Threaded
Open this post in threaded view
|

Re: Matching Empty maps

Raimo Niskanen-2
In reply to this post by Joe Armstrong-2
On Tue, Feb 07, 2017 at 12:45:15PM +0100, Joe Armstrong wrote:

> Ten minutes ago I was happily recursing down a list and discovered
> to my horror that an empty map isn't an empty map.
>
> 1> #{} = #{a => 1}.
> #{a => 1}
>
> The documentation actually says:
>
> <quote>
> #{} = Expr
>
> This expression matches if the expression Expr is of type map,
> otherwise it fails with an exception badmatch.
> </quote>
>
> So #{} is an empty map in an argument position but not an empty map
> in a pattern.
>
> So this is not a bug since the system does what the documentation says
> but it is very weird.
>
> Is there some deep reason for this that I've missed ??????
>
> Very Puzzled

I think it is quite logical since #{a := _} in a match position matches a
map with a key 'a' plus any number of other keys in it, so why should not
the empty map #{} in a match position also match any number of other keys
in it?

>
> /Joe

--

/ Raimo Niskanen, Erlang/OTP, Ericsson AB
_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
Reply | Threaded
Open this post in threaded view
|

Re: Matching Empty maps

Jesper Louis Andersen-2
The alternative notation is something along the lines of:

#{ ... }

which says that we have a map with at least one extra undefined element. In that case, the pattern

#{ a := _, ... }

would say "the key a MUST be present, I don't care about the value, and there MUST be additional elements in the map", whereas

#{ a := _ }

is *exactly* the one-element map. Too late for this notation though.

On Tue, Feb 7, 2017 at 3:48 PM Raimo Niskanen <[hidden email]> wrote:
On Tue, Feb 07, 2017 at 12:45:15PM +0100, Joe Armstrong wrote:
> Ten minutes ago I was happily recursing down a list and discovered
> to my horror that an empty map isn't an empty map.
>
> 1> #{} = #{a => 1}.
> #{a => 1}
>
> The documentation actually says:
>
> <quote>
> #{} = Expr
>
> This expression matches if the expression Expr is of type map,
> otherwise it fails with an exception badmatch.
> </quote>
>
> So #{} is an empty map in an argument position but not an empty map
> in a pattern.
>
> So this is not a bug since the system does what the documentation says
> but it is very weird.
>
> Is there some deep reason for this that I've missed ??????
>
> Very Puzzled

I think it is quite logical since #{a := _} in a match position matches a
map with a key 'a' plus any number of other keys in it, so why should not
the empty map #{} in a match position also match any number of other keys
in it?

>
> /Joe

--

/ Raimo Niskanen, Erlang/OTP, Ericsson AB
_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions

_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
Reply | Threaded
Open this post in threaded view
|

Re: Matching Empty maps

Björn-Egil Dahlberg XB
In reply to this post by Joe Armstrong-2
On 02/07/2017 12:45 PM, Joe Armstrong wrote:
> So #{} is an empty map in an argument position but not an empty map
> in a pattern.
Yes, of course!

There is a difference between patterns and values. They are not the same
thing.

A pattern does not need to describe the entire thing in match. It just
has to describe the things it needs to match.

Records are the precursor to the map behavior of course. For example,

-record(r, {a,b,c}).

foo(#r{}=R) ->
     R.

// Björn-Egil

_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
Reply | Threaded
Open this post in threaded view
|

Re: Matching Empty maps

Richard A. O'Keefe-2
In reply to this post by Jesper Louis Andersen-2
The frames proposal did something similar.
I tried the experiment of requiring |_ to say
"other things can be present", with the absence
of this meaning exact key agreement.

But writing sample programs I found that I was
CONSTANTLY leaving the |_ out when it should have
been there, and of course it missed half of the
*point* of using records/frames/maps, namely that
you can add a new field without breaking existing
code.



_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions