Thread overview
[Issue 7909] New: to!(enum)(string) and to!(string)(enum) break when enum is integral
Apr 14, 2012
Adam D. Ruppe
Apr 14, 2012
Adam D. Ruppe
Apr 14, 2012
Adam D. Ruppe
Apr 15, 2012
Kenji Hara
April 14, 2012
http://d.puremagic.com/issues/show_bug.cgi?id=7909

           Summary: to!(enum)(string) and to!(string)(enum) break when
                    enum is integral
           Product: D
           Version: D2
          Platform: All
        OS/Version: All
            Status: NEW
          Severity: regression
          Priority: P2
         Component: Phobos
        AssignedTo: nobody@puremagic.com
        ReportedBy: destructionator@gmail.com


--- Comment #0 from Adam D. Ruppe <destructionator@gmail.com> 2012-04-14 07:19:59 PDT ---
import std.conv;

enum Test { a = -1, b = 0, c = 1 }

void main() {
    assert(to!string(Test.a) == "a"); // matches more than one
    assert(to!Test("b") == Test.b); // does not match anything
}

First line error:
Error: template std.conv.toImpl matches more than one template declaration,
src/phobos/std/conv.d(1034):toImpl(T,S) if (!isImplicitlyConvertible!(S,T) &&
is(S == enum) && isSomeString!(T)) and src/phobos/std/conv.d(1155):toImpl(T,S)
if (isIntegral!(S) && isSigned!(S) && isSomeString!(T))
e.d(6): Error: template instance std.conv.to!(string).to!(Test) error
instantiating


Second line error:
src/phobos/std/conv.d(244): Error: template std.conv.toImpl does not match any
function template declaration
src/phobos/std/conv.d(244): Error: template std.conv.toImpl cannot deduce
template function from argument types !(Test)(string)
src/phobos/std/conv.d(244): Error: template instance toImpl!(Test) errors
instantiating template
e.d(7): Error: template instance std.conv.to!(Test).to!(string) error
instantiating




This worked correctly on dmd 2.058.


Note that if you use an enum without assigned values (enum Test {a,b,c}), it
still works.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
April 14, 2012
http://d.puremagic.com/issues/show_bug.cgi?id=7909



--- Comment #1 from Adam D. Ruppe <destructionator@gmail.com> 2012-04-14 07:26:07 PDT ---
static assert(isIntegral!(Test));
fails on .58, passes on .59. This is what causes the matches more than one
error.

Though, interesting to note that:
        static assert(is(Test : int));
passes on both .58 and 59.


It might be some kind of compiler overload resolution change that broke things; isIntegral is implemented with that.

The compiler might have changed for correctness (I'm not really sure yet), but the Phobos behavior used to be good and now isn't, so I still call it a phobos regression.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
April 14, 2012
http://d.puremagic.com/issues/show_bug.cgi?id=7909



--- Comment #2 from Adam D. Ruppe <destructionator@gmail.com> 2012-04-14 07:57:10 PDT ---
Well, a simple enough fix for the first one is to tighten up the constraint on toImpl for the isIntegral one.

Line 1156 of conv.d, add: !is(S == enum).

Doesn't seem to break anything (indeed, if isIntegral used to always return false on enums, it'd just be restoring the previous behavior anyway).



Now, for the parsing side. We can do basically the same thing.

Line 1708 of conv.d, add: && !is(Target == enum).

That takes the isIntegral variety out of consideration, and then it uses the correct enum version.

Strange that it didn't say "matches more than one" again, since it is basically the same thing, but meh, whatever, this fixes it and didn't break the other cases I tried.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
April 15, 2012
http://d.puremagic.com/issues/show_bug.cgi?id=7909


Kenji Hara <k.hara.pg@gmail.com> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
           Keywords|                            |pull, rejects-valid


--- Comment #3 from Kenji Hara <k.hara.pg@gmail.com> 2012-04-14 20:45:05 PDT ---
https://github.com/D-Programming-Language/phobos/pull/537

(In reply to comment #1)
> static assert(isIntegral!(Test));
> fails on .58, passes on .59. This is what causes the matches more than one
> error.
> 
> Though, interesting to note that:
>         static assert(is(Test : int));
> passes on both .58 and 59.
> 
> 
> It might be some kind of compiler overload resolution change that broke things; isIntegral is implemented with that.
> 
> The compiler might have changed for correctness (I'm not really sure yet), but the Phobos behavior used to be good and now isn't, so I still call it a phobos regression.

Yes, this is 2.059 Phobos regression, not compilers.
As you mentioned, isIntegral!T should return false if T is enum type.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------