Thread overview
RFC: Fixing std.typecons.Typedef
Sep 02, 2016
Meta
Sep 02, 2016
Meta
Sep 03, 2016
Lodovico Giaretta
Sep 05, 2016
Chris Wright
September 02, 2016
I was thinking about how to fix Typedef the other day and came up with a way of generating a guaranteed unique ID for each instantiation, even if they are on the same line:

alias FixedTypedef(T, T init = T.init, string cookie = new class {}.stringof) = Typedef(T, init, cookie);

alias Test1 = FixedTypedef!int, Test2 = FixedTypedef!int;

assert(!is(Test1 == Test2)); //Passes

What I'd like to know is if there might be a better way of doing this. For each instantiation of FixedTypedef, there's a new class being created and stored in the executable (I think), as well as their .stringof. This could cause a lot of bloat if Typedef is being used heavily.

Furthermore, would this be considered a code breakage? Looking at http://dlang.org/phobos/std_typecons.html#.Typedef, it says:

"Typedef allows the creation of a unique type which is based on an existing type. Unlike the alias feature, Typedef ensures the two types are not considered as equals."

This implies that the current behaviour of Typedef is a bug, and thus fixing it would not be code breakage. However, people may have come to depend on this bug and fixing it would break code. Thirdly, there is no point in having Typedef behave as it currently does by default, which is similar to how aliases behave. Example:

alias NewDouble = Typedef!double;
assert(!is(NewDouble == double)); //Okay, not the same type as expected

alias NewInt1 = Typedef!int;
alias NewInt2 = Typedef!int;
assert(is(NewInt1 == NewInt2)); //Passes?!

Thoughts? Opinions? I think it'd be nice to have a typedef that works correctly by default.
September 02, 2016
On Friday, 2 September 2016 at 19:40:52 UTC, Meta wrote:
> I was thinking about how to fix Typedef the other day and came up with a way of generating a guaranteed unique ID for each instantiation, even if they are on the same line:
>
> alias FixedTypedef(T, T init = T.init, string cookie = new class {}.stringof) = Typedef(T, init, cookie);
>
> alias Test1 = FixedTypedef!int, Test2 = FixedTypedef!int;
>
> assert(!is(Test1 == Test2)); //Passes
>
> What I'd like to know is if there might be a better way of doing this. For each instantiation of FixedTypedef, there's a new class being created and stored in the executable (I think), as well as their .stringof. This could cause a lot of bloat if Typedef is being used heavily.
>
> Furthermore, would this be considered a code breakage? Looking at http://dlang.org/phobos/std_typecons.html#.Typedef, it says:
>
> "Typedef allows the creation of a unique type which is based on an existing type. Unlike the alias feature, Typedef ensures the two types are not considered as equals."
>
> This implies that the current behaviour of Typedef is a bug, and thus fixing it would not be code breakage. However, people may have come to depend on this bug and fixing it would break code. Thirdly, there is no point in having Typedef behave as it currently does by default, which is similar to how aliases behave. Example:
>
> alias NewDouble = Typedef!double;
> assert(!is(NewDouble == double)); //Okay, not the same type as expected
>
> alias NewInt1 = Typedef!int;
> alias NewInt2 = Typedef!int;
> assert(is(NewInt1 == NewInt2)); //Passes?!
>
> Thoughts? Opinions? I think it'd be nice to have a typedef that works correctly by default.

Why did my auto-generated gravatar picture change?
September 03, 2016
On Friday, 2 September 2016 at 19:40:52 UTC, Meta wrote:
> I was thinking about how to fix Typedef the other day and came up with a way of generating a guaranteed unique ID for each instantiation, even if they are on the same line:
>
> [...]
>
> What I'd like to know is if there might be a better way of doing this. For each instantiation of FixedTypedef, there's a new class being created and stored in the executable (I think), as well as their .stringof. This could cause a lot of bloat if Typedef is being used heavily.

IMHO, a better solution would be a __UNIQUE_UUID__ special token, which the compiler replaces with a randomly generated (or guaranteed unique, if we cannot afford a strong enough random algorithm) UUID (or identifier, or whatever you prefer).

But if we cannot have it, a library function that does what you propose may be useful, as unique strings may also be helpful in other places.

> Furthermore, would this be considered a code breakage? Looking at http://dlang.org/phobos/std_typecons.html#.Typedef, it says:
>
> "Typedef allows the creation of a unique type which is based on an existing type. Unlike the alias feature, Typedef ensures the two types are not considered as equals."
>
> This implies that the current behaviour of Typedef is a bug, and thus fixing it would not be code breakage. However, people may have come to depend on this bug and fixing it would break code. Thirdly, there is no point in having Typedef behave as it currently does by default, which is similar to how aliases behave. Example:
>
> alias NewDouble = Typedef!double;
> assert(!is(NewDouble == double)); //Okay, not the same type as expected
>
> alias NewInt1 = Typedef!int;
> alias NewInt2 = Typedef!int;
> assert(is(NewInt1 == NewInt2)); //Passes?!

I see the current behaviour not as a bug, but as a not-well-documented feature. In fact, the current behaviour allows you to create families of types which are considered equal. This method is different from `alias`, as it is based on strings and thus it does not require visibility of the aliased type.

What we surely want is an easy way to guarantee that a Typedef is in fact unique. This can be done with another template `UniqueTypedef`, or having an easy way to generate unique strings (see my idea above):

alias t = Typedef!(int, int.init, __UNIQUE_UUID__);
September 05, 2016
On Sat, 03 Sep 2016 11:34:02 +0000, Lodovico Giaretta wrote:
> I see the current behaviour not as a bug, but as a not-well-documented feature.

It's the default behavior, though, and it does nearly the opposite of what you probably want.