Potential issue with DMD where the template constrains are not evaluated early enough to prevent type recursion

Georgi D via Digitalmars-d digitalmars-d at puremagic.com
Fri May 13 14:21:27 PDT 2016


Hi,

I have the following code which should compile in my opinion:

struct Foo {}

import std.range.primitives;
import std.algorithm.iteration : map, joiner;

auto toChars(R)(R r) if (isInputRange!R)
{
    return r.map!(toChars).joiner(", ");
}

auto toChars(Foo f)
{
    import std.range : chain;
    return chain("foo", "bar");
}

void main()
{
    import std.range : repeat;
    Foo f;
    auto r = f.repeat(3);
    auto chars = r.toChars();
}

But fails to compile with the following error:

Error: template instance 
std.algorithm.iteration.MapResult!(toChars, Take!(Repeat!(Foo))) 
forward reference of function toChars

The reason it fails to compile in my opinion is that the template 
constraint fails to remove the generic toChars from the list 
possible matches early enough so the compiler thinks there is a 
recursive call and cannot deduce the return type.

Just changing the name of the generic toChars to anything else 
makes the code compile:

struct Foo {}

import std.range.primitives;
import std.algorithm.iteration : map, joiner;

auto toCharsRange(R)(R r) if (isInputRange!R)
{
    return r.map!(toChars).joiner(", ");
}

auto toChars(Foo f)
{
    import std.range : chain;
    return chain("foo", "bar");
}

void main()
{
    import std.range : repeat;
    Foo f;
    auto r = f.repeat(3);
    auto chars = r.toCharsRange();
}

Compiles just fine.





More information about the Digitalmars-d mailing list