[erlang-questions] A (probable) dialyzer misconception?

Eric Merritt <>
Tue Nov 15 17:39:49 CET 2011


Hello All,

I recently added dialyzer support back to sinan. I am using it
again to clean up potential problems with various Erlware
projects. Perhaps naively I have turned on all warnings.  The
warnings turned on are as follows:

     no_return,
     no_unused,
     no_improper_lists,
     no_fun_app,
     no_match,
     no_opaque,
     no_fail_call,
     error_handling,
     race_conditions,
     behaviours,
     unmatched_returns,
     overspecs,
     underspecs,
     specdiffs

I have run into an issue that has me stumped. I suspect it is due
to an expectation of how dialyzer operates on my part that is
simply not true. If you run dialyzer on the attached file with
all the warnings enabled you get the following output.

the types are specified in the file, but just for brevity look
like this.

-type dictionary(K, V) :: {ec_assoc_list,
                           [{key(K),
                             value(V)}]}.
-type key(K) :: K.
-type value(V) :: V.

Lets take has_key. The spec and function are defined as follows.

-spec has_key(key(_K), Object::dictionary(_K, _V))  ->
                     boolean().
has_key(Key, {ec_assoc_list, Data}) ->
    lists:keymember(Key, 1, Data).

What I am assuming here is that I am declaring to the world that
this function takes a key (which can be whatever the caller
determines it to be) and a dictionary and returns true |
false. Dialyzer seems to be infering the type of data as
'maybe_improper_list' somehow and then warning me that the spec
is wron"g. Actually it warns me that the dictionary is a subtype
of maybe_improper_list. Well, thats very true and correct I
believe in this case, the has_key function takes a list in a
specific format. Thats why the spec defines it in that way. That
being the case, why is dialyzer warning me about this problem?
You can see all the warnings below, the error for has_key is on
line 25. All of these warnings are variations of the subtype
warning for the most part. Any insight would be appreciated.


ec_dialyzer_test.erl:25: Type specification
ec_dialyzer_test:has_key(key(_K),Object::dictionary(_K,_V)) ->
boolean() is a subtype of the success typing:
ec_dialyzer_test:has_key(_,{'ec_assoc_list',maybe_improper_list()}) ->
boolean()
ec_dialyzer_test.erl:30: Type specification
ec_dialyzer_test:get(key(K),Object::dictionary(K,V)) -> value(V) is a
subtype of the success typing:
ec_dialyzer_test:get(_,{'ec_assoc_list',maybe_improper_list()}) ->
any()
ec_dialyzer_test.erl:39: Type specification
ec_dialyzer_test:from_list([{key(K),value(V)}]) -> dictionary(K,V) is
a subtype of the success typing:
ec_dialyzer_test:from_list(maybe_improper_list()) ->
{'ec_assoc_list',maybe_improper_list()}
ec_dialyzer_test.erl:44: Type specification
ec_dialyzer_test:keys(dictionary(K,_V)) -> [key(K)] is a subtype of
the success typing: ec_dialyzer_test:keys({'ec_assoc_list',[any()]})
-> [any()]
-------------- next part --------------
A non-text attachment was scrubbed...
Name: ec_dialyzer_test.erl
Type: text/x-erlang
Size: 1300 bytes
Desc: not available
URL: <http://erlang.org/pipermail/erlang-questions/attachments/20111115/2e338393/attachment.bin>


More information about the erlang-questions mailing list