Comment #0 by bearophile_hugs — 2011-09-07T02:10:03Z
This is a bug report. I have found two different problems while creating a fixed-sized array as long as the number members of an enum (DMD 2.055beta3):
import std.traits: EnumMembers;
enum Foo : size_t { A = 0, B = 1, C = 2 }
void main() {
int[(EnumMembers!(Foo)).length] bar1; // Error: EnumMembers!(Foo) is used as a type
enum size_t nmembers0 = (EnumMembers!(Foo)).length; // Error: EnumMembers!(Foo) is used as a type
alias EnumMembers!(Foo) members;
int[members.length] bar2; // Error: identifier 'length' of 'members.length' is not defined
enum size_t nmembers = members.length;
int[nmembers] bar3; // OK
}
---------------
In practice I think a length attribute for enums is handy to have (this is a low-priority enhacement request):
enum Foo : size_t { A = 0, B = 1, C = 2 }
void main() {
int[Foo.length] bar;
}
Comment #1 by tommitissari — 2012-07-16T10:14:48Z
(In reply to comment #0)
> In practice I think a length attribute for enums is handy to have (this is a
> low-priority enhacement request):
I think it's a good enhancement, but instead of "length" it should be called "count".
Tool {hammer, drill, screwdriver}
Tool.count; // a lot better than Tool.length
Comment #2 by andrej.mitrovich — 2012-12-02T10:06:34Z
(In reply to comment #0)
> This is a bug report. I have found two different problems while creating a
> fixed-sized array as long as the number members of an enum (DMD 2.055beta3)
All of these now work.
> In practice I think a length attribute for enums is handy to have (this is a
> low-priority enhacement request):
> enum Foo : size_t { A = 0, B = 1, C = 2 }
> void main() {
> int[Foo.length] bar;
> }
The problem with this is that lookups also go to the base type of the enum, so:
struct T
{
@property static size_t length() { return 0; }
}
enum Foo : T { a = T() }
void main()
{
assert(Foo.length == 1); // fails
}
We could instead provide a template in std.traits:
template EnumLength(E) if (is(E == enum))
{
enum size_t EnumLength = EnumMembers!E.length;
}
void main()
{
assert(EnumLength!Foo == 1);
}
Comment #3 by bearophile_hugs — 2012-12-02T10:32:59Z
(In reply to comment #2)
> (In reply to comment #0)
> > This is a bug report. I have found two different problems while creating a
> > fixed-sized array as long as the number members of an enum (DMD 2.055beta3)
>
> All of these now work.
Right, I close this bug report. Issue 4997 covers the enhancement request.
> The problem with this is that lookups also go to the base type of the enum, so:
>
> struct T
> {
> @property static size_t length() { return 0; }
> }
>
> enum Foo : T { a = T() }
>
> void main()
> {
> assert(Foo.length == 1); // fails
> }
Enums already have some built-in attributes, that cause some troubles. In Issue 4997 I have suggested a namespace named "meta", so you write "MyEnum.meta.length". But then a problem is that MyEnum.meta.max breaks the convention that D integral types have a "max" attribute.
Comment #4 by bearophile_hugs — 2012-12-02T10:34:49Z
(In reply to comment #2)
> We could instead provide a template in std.traits:
>
> template EnumLength(E) if (is(E == enum))
> {
> enum size_t EnumLength = EnumMembers!E.length;
> }
>
> void main()
> {
> assert(EnumLength!Foo == 1);
> }
I think this gives too much little improvement :-) Such EnumLength template is not needed in Phobos.
Comment #5 by andrej.mitrovich — 2012-12-02T10:52:48Z
(In reply to comment #3)
> Enums already have some built-in attributes, that cause some troubles. In
> Issue 4997 I have suggested a namespace named "meta", so you write
> "MyEnum.meta.length".
This is also implementable via a template that exposes some fields that you need. There's no need to hack around the compiler for this.