[erlang-questions] Dialyzer type specifications for macros with bitstrings makes erlc barf

zxq9 zxq9@REDACTED
Fri Mar 18 06:52:21 CET 2016


On 2016年3月17日 木曜日 21:53:06 Sachin Panemangalore wrote:
> 1. The following compiles fine in Erlang.
> 
> -define(MY_INT_MACRO1, 1).
> -define(MY_INT_MACRO2, 2).
> -type my_type() :: ?MY_INT_MACRO1 |  ?MY_INT_MACRO2 .
> 
> 
> 2. The following doesn't
> 
> -define(MY_BITSTRING_MACRO1, <<"01">>).
> -define(MY_BITSTRING_MACRO2, <<"02">>).
> -type my_type() :: ?MY_BITSTRING_MACRO1 |  ?MY_BITSTRING_ MACRO2 .
> 
> Why ? and is there a way to make this work ?

(Changed the names above to say what I think you meant.)

Type declarations have a few limitations with regard to defining what is
inside. You can declare the size of a binary, but not what it contains,
hence these sort of type definitions:
https://github.com/zxq9/zuuid/blob/master/src/zuuid.erl#L47-L56

In the same way, you can declare a dictionary or map's k/v types:

-type my_dict() :: dict:dict(atom(), integer()).
-type my_map()  :: maps:map(atom(), string()).

You'll never be able to provide a complete, fixed shape of a dict or
map, though, because that would actually be a schema, and that's what
using tuple or records as types already does. This only turns out to
be the same limitation as we have defining lists of things:

-type my_tuple_list() :: [{atom(), some_type()}].

This is why the following is not legal:

-type some_phrase() :: "I am a string literal.".

Actually, I think you can't even declare a list of some specific length,
which leaves binary type definitions slightly more rigorous than lists. But
if you *knew* the length of a list why wouldn't you be using a tuple?

It would be pretty convenient to be able to define types based on binary
literals, since their use case differs from binaries. But on the other hand,
if you want binary strings defined this way you usually actually want atoms
that you can derive from some external binary data you receive -- and atoms
are (usually) an excellent way to clean up your type defs in
self-documenting ways.

-Craig



More information about the erlang-questions mailing list