Thread overview
[Issue 6557] New: Inplace enum literals
Aug 26, 2011
Kenji Hara
Aug 27, 2011
Kenji Hara
August 26, 2011
http://d.puremagic.com/issues/show_bug.cgi?id=6557

           Summary: Inplace enum literals
           Product: D
           Version: D2
          Platform: All
        OS/Version: All
            Status: NEW
          Severity: enhancement
          Priority: P2
         Component: DMD
        AssignedTo: nobody@puremagic.com
        ReportedBy: bearophile_hugs@eml.cc


--- Comment #0 from bearophile_hugs@eml.cc 2011-08-26 04:33:05 PDT ---
This is a low-priority additive enhancement request, maybe for D3.

This is a commonly asked enhancement. I add it here because it's good to have this entry as a reference place for present and future discussions about this idea, and because I think I have found a way to solve one downside usual found in this idea.

Note: this enhancement request does _not_ replace the usefulness of named arguments, it's more like a complement of them.


Nude boolean arguments are often ambiguous for the people that read the code. Some examples of lines from real code of real frameworks in other languages:

widget.repaint(false);
var opacitySlider = new Slider(true);
stackView.updateHeight(false);
widget.next(true);


The idea to avoid such ambiguity is to use one enum. But it's more handy to define the enum in-place in the function/method signature:


void foo(enum {a, b} arg) {
    if (arg == b) {}
    if (arg == foo.a) {} // alternative syntax
}
void main() {
    foo(a);                // OK, allowed
    foo(foo.a);            // alternative syntax
    auto input = foo.b;    // OK
    foo(input);            // OK
    alias typeof(foo.a) E; // OK
}


The simple syntax functionName.enumEntry solves the problem of referencing enum entries from outside the function.

Some special cases. This is acceptable, they are two overloads of foo() (this
needs strongly typed enums, see issue 3999 ):

void foo(int arg) {}
void foo(enum {a, b} arg) {}

If enums are not strongly typed then I presume that overload needs to be statically refused.


This is not acceptetable, it's compile-time error:

void bar(enum {a, b} arg) {}
void bar(enum {a, c, d} arg) {}

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
August 26, 2011
http://d.puremagic.com/issues/show_bug.cgi?id=6557



--- Comment #1 from Kenji Hara <k.hara.pg@gmail.com> 2011-08-26 05:14:00 PDT ---
> void foo(enum {a, b} arg) {
>     if (arg == b) {}
>     if (arg == foo.a) {} // alternative syntax
> }

I have one question.
In following case, what does foo receive as arg?

void main()
{
    typeof(foo.a) E;
    E a = foo.b;
    foo(a);   // == foo(foo.a) or foo(foo.b) ?
}

I think the enum scope inference from their member name is nearly impossible,
because D has template function.
The feature requires a function signature to determine the argument types, but
template function call requires argument types to determine the function
signature!

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
August 26, 2011
http://d.puremagic.com/issues/show_bug.cgi?id=6557



--- Comment #2 from bearophile_hugs@eml.cc 2011-08-26 16:31:38 PDT ---
(In reply to comment #1)

> In following case, what does foo receive as arg?
> 
> void main()
> {
>     typeof(foo.a) E;
>     E a = foo.b;
>     foo(a);   // == foo(foo.a) or foo(foo.b) ?
> }

Thank you for finding this problem. I think that's a quite uncommon case, it's a bug of the programmer. So this bad corner case is not enough to kill the whole idea. In this case of actual ambiguity I think D has to act like in this case:


struct Foo {
    int x;
}
void main() {
    int x;
    Foo f;
    with (f)
        x++; // line 8, error
    with (f) {} // no error here, no actual ambiguity
}

test.d(8): Error: with symbol test.Foo.x is shadowing local symbol test.main.x



void foo(enum {a, b} arg) {}
void main() {
    auto a = foo.b;
    foo(a); // Error: ambiguity...
}

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
August 27, 2011
http://d.puremagic.com/issues/show_bug.cgi?id=6557



--- Comment #3 from bearophile_hugs@eml.cc 2011-08-27 05:06:36 PDT ---
(In reply to comment #1)

> I think the enum scope inference from their member name is nearly impossible,
> because D has template function.
> The feature requires a function signature to determine the argument types, but
> template function call requires argument types to determine the function
> signature!

Do you mean this problem?

void foo(T)(T x, enum : T { A, B }) {}
void main() {
    typeof(foo.A) a = foo.B;
    foo(a);
}

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
August 27, 2011
http://d.puremagic.com/issues/show_bug.cgi?id=6557



--- Comment #4 from Kenji Hara <k.hara.pg@gmail.com> 2011-08-27 07:15:29 PDT ---
My thought case is following code.

void foo()(int n){} // 1
void foo()(enum {a, b} arg) {} // 2

void main() {
  int a;
  foo(a);  // 1 or 2 ?
}

To determine the signature of foo, 'a' is judged as integer typed variable, and
1st foo overload is selected. 2nd version of foo is never selected.
And this is natural behavior guided from the current specification.

But this enhancement is require to determine foo's signature *before* argument types. This is a serious conflict.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
September 09, 2011
http://d.puremagic.com/issues/show_bug.cgi?id=6557


bearophile_hugs@eml.cc changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|NEW                         |RESOLVED
         Resolution|                            |INVALID


--- Comment #5 from bearophile_hugs@eml.cc 2011-09-09 03:14:19 PDT ---
The basic idea is cute, but I think it currently doesn't work. So I close this enhancement request, to be reopened if better ideas come.

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