ranges of characters and the overabundance of traits that go with them

Jonathan M Davis via Digitalmars-d digitalmars-d at puremagic.com
Sun Mar 12 13:31:10 PDT 2017


On Sunday, March 12, 2017 17:22:09 Jack Stouffer via Digitalmars-d wrote:
> On Sunday, 12 March 2017 at 09:26:08 UTC, Jonathan M Davis wrote:
> > and in that case, we're stuck doing _something_ to accept the
> > implicit conversions, or we break code.
>
> Sorry wrote that at 4 in the morning. Should have been clearer.
>
> I'm saying we should, at best, offer an overload for alias
> this-ed structs only temporarily as a deprecated function. As I
> mentioned, I don't like these hacks, and in reality Phobos
> requires a lot more of them in order to be regression free. They
> also clutter up the code and docs.

Yes, they clutter up code, but I don't know how reasonable it is to keep
deprecating behavior in Phobos like that every time that we get around to
templatizing a string-based function so that it's range based. To make
matters worse, I don't think that it's actually possible to deprecate the
implicit conversions _and_ have it be safe in the case where a portion of
the range is returned from the function.

If isConvertibleToString is used - or any template constraint that is
templated on the whole type - then when the implicit conversion is done,
it's done inside the function, which in the case of static arrays and some
user-defined types would mean returning a reference to memory that is local
to the function (and thus invalid), whereas if the function is templated on
the character type, then the implict conversion occurs at the call site - so
it acts as it did when the function wasn't templated, and it's safe. But if
the function is templated on character type, then it's going to accept
strings, not just the implicit conversions. So, you can't deprecate it. So,
it looks to me like we're faced with either allowing deprecation and being
unsafe or being safe and not being able to do any deprecation. Certainly, I
can't think of any other way to accept an implicit conversion and have the
conversion be done at the call site, and without that, you have a safety
problem.

As such, even if the resulting breakage is acceptable, I don't see how we be
safely templatizing these functions and then deprecating the overloads that
deal with implicit conversions. In some cases, we could get away with it,
because no portion of the original range is returned, but in many cases, it
is returned, and then AFAIK, templatizing on the character type is the only
way to make it safe.

This whole problem would be reduced if we could actually get the implicit
conversion of static arrays to dynamic arrays deprecated and then removed
from the language, but last time I checked, Walter didn't like that idea,
and even if we did that, we'd still have the potential of something unsafe
happening with user-defined types implicitly converting to string where they
work correctly when the function does the conversion at the call site but do
not work correctly if the conversion is done internally.

Honestly, this issue feels a lot to me like the issue with isSomeString.
Ideally, we'd just fix it and deal with the broken code, as annoying as that
would be. But if we did that, we'd be breaking code. We can make a choice
that makes the language or library better in the long run, but it's going to
cost us in the short term.

In _some_ cases we could go through a deprecation phase with the implicit
conversions and avoid immediately breaking code, but it's likely to result
in a number of complaints if we do, and in many cases, we simply can't do it
safely - not unless someone has a bright idea about how we can force
implicit conversions to take place at the call site while still having the
function be templated on the entire type rather than just the character
type.

- Jonathan M Davis



More information about the Digitalmars-d mailing list