www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - Subtyping of an enum

reply Anton Fediushin <fediushin.anton yandex.com> writes:
Hello! I am currently trying to add a custom `toString` method to 
an enum so that:
1. Enum members would still have numeric values and can be easily 
compared (things like `enum a { foo = "FOO", bar = "BAR”}` won't 
do, I want `a.foo < a.bar)`)
2. More custom methods can be implemented in the future

Obvious solution is to wrap an enum in a structure and utilize 
'alias this' for subtyping like this:
```
struct Enum {
   private {
     enum internal {
       foo,
       bar
     }
     internal m_enum;
   }
   this(internal i) { m_enum = i; }
   alias m_enum this;
   string toString() {
     // custom implementation of toString
   }
}
```

This seems to work just fine for assigning and comparisons but 
passing Enum as a function argument does not work:
```
void fun(Enum e) {}

fun(Enum.foo);
---
Error: function fun(Enum e) is not callable using argument types 
(internal)
Cannot pass argument foo of type internal to parameter Enum e.
```

Of course, I could just define a bunch of functions that accept 
my enum as the first argument and call them using UFCS but it'd 
require to explicitly specify functions instead of D taking care 
of that (toString() for structures is called automagically by 
functions like writeln) and those functions would hang around 
here and there totally unorganized. I prefer to keep functions 
inside of structures and classes.

If there are other ways of achieving the same *and* keeping code 
clean and organized, please share.

Thank you in advance,
Anton.
Apr 15 2019
next sibling parent reply Alex <sascha.orlov gmail.com> writes:
On Monday, 15 April 2019 at 08:39:24 UTC, Anton Fediushin wrote:
 Hello! I am currently trying to add a custom `toString` method 
 to an enum so that:
 1. Enum members would still have numeric values and can be 
 easily compared (things like `enum a { foo = "FOO", bar = 
 "BAR”}` won't do, I want `a.foo < a.bar)`)
 2. More custom methods can be implemented in the future

 Obvious solution is to wrap an enum in a structure and utilize 
 'alias this' for subtyping like this:
 ```
 struct Enum {
   private {
     enum internal {
       foo,
       bar
     }
     internal m_enum;
   }
   this(internal i) { m_enum = i; }
   alias m_enum this;
   string toString() {
     // custom implementation of toString
   }
 }
 ```

 This seems to work just fine for assigning and comparisons but 
 passing Enum as a function argument does not work:
 ```
 void fun(Enum e) {}

 fun(Enum.foo);
 ---
 Error: function fun(Enum e) is not callable using argument 
 types (internal)
 Cannot pass argument foo of type internal to parameter Enum e.
 ```

 Of course, I could just define a bunch of functions that accept 
 my enum as the first argument and call them using UFCS but it'd 
 require to explicitly specify functions instead of D taking 
 care of that (toString() for structures is called automagically 
 by functions like writeln) and those functions would hang 
 around here and there totally unorganized. I prefer to keep 
 functions inside of structures and classes.
Isn't this a reason for passing your internals encapsulated, like ´´´ Enum EnumInstance = Enum(Enum.internal.foo); fun(EnumInstance); ´´´ ?
 If there are other ways of achieving the same *and* keeping 
 code clean and organized, please share.

 Thank you in advance,
 Anton.
Otherwise, you could alwas define fun as ´´´ void fun(Enum.internal e) {} ´´´ but I assume, you want to avoid especially this. In favor of my first proposition, also speaks the fact, that Enum.foo is somewhat awkward w.r.t. your question, as you treat the internal enum as a static member. Was this intended?
Apr 15 2019
parent reply Anton Fediushin <fediushin.anton yandex.com> writes:
On Monday, 15 April 2019 at 10:00:36 UTC, Alex wrote:
 On Monday, 15 April 2019 at 08:39:24 UTC, Anton Fediushin wrote:
 [snip]
Otherwise, you could alwas define fun as ´´´ void fun(Enum.internal e) {} ´´´ but I assume, you want to avoid especially this. In favor of my first proposition, also speaks the fact, that Enum.foo is somewhat awkward w.r.t. your question, as you treat the internal enum as a static member. Was this intended?
Enum.internal is private to make it inaccessible from any other place. All I want is a way to have an enum that I could extend with my own methods. Something to make the following code work: ``` Enum a = Enum.foo; Enum b = Enum.bar; assert(a == Enum.foo); assert(a < b); assert(a.toString == "FOO"); assert(b.toString == "BAR"); writeln(a); // FOO writeln(b); // BAR ```
Apr 15 2019
parent reply Alex <sascha.orlov gmail.com> writes:
On Monday, 15 April 2019 at 10:15:50 UTC, Anton Fediushin wrote:
 On Monday, 15 April 2019 at 10:00:36 UTC, Alex wrote:

 Enum.internal is private to make it inaccessible from any other 
 place. All I want is a way to have an enum that I could extend 
 with my own methods.

 Something to make the following code work:
 ```
 Enum a = Enum.foo;
 Enum b = Enum.bar;
 assert(a == Enum.foo);
 assert(a < b);
 assert(a.toString == "FOO");
 assert(b.toString == "BAR");
 writeln(a); // FOO
 writeln(b); // BAR
 ```
This would: ´´´ struct Enum { private { enum internal { foo, bar } internal m_enum; } this(internal i) { m_enum = i; } alias m_enum this; string toString() { if(m_enum == internal.foo) return "FOO"; else return "BAR"; } } void fun(Enum e) {} void main(){ import std.stdio; fun(Enum.init); Enum a = Enum.foo; Enum b = Enum.bar; assert(a == Enum.foo); assert(a < b); assert(a.toString == "FOO"); assert(b.toString == "BAR"); writeln(a); // FOO writeln(b); // BAR } ´´´ Assuming, that automatic generation of "FOO" from foo was not part of your question :-p
Apr 15 2019
parent reply Anton Fediushin <fediushin.anton yandex.com> writes:
On Monday, 15 April 2019 at 10:45:26 UTC, Alex wrote:
 On Monday, 15 April 2019 at 10:15:50 UTC, Anton Fediushin wrote:
 On Monday, 15 April 2019 at 10:00:36 UTC, Alex wrote:
 [snip]
This would: ´´´ struct Enum { private { enum internal { foo, bar } internal m_enum; } this(internal i) { m_enum = i; } alias m_enum this; string toString() { if(m_enum == internal.foo) return "FOO"; else return "BAR"; } } void fun(Enum e) {} void main(){ import std.stdio; fun(Enum.init); Enum a = Enum.foo; Enum b = Enum.bar; assert(a == Enum.foo); assert(a < b); assert(a.toString == "FOO"); assert(b.toString == "BAR"); writeln(a); // FOO writeln(b); // BAR } ´´´ Assuming, that automatic generation of "FOO" from foo was not part of your question :-p
This does work unless I want to use it like this: ``` fun(Enum.foo); --- Error: function fun(Enum e) is not callable using argument types (internal) cannot pass argument foo of type internal to parameter Enum e ```
Apr 15 2019
parent Alex <sascha.orlov gmail.com> writes:
On Monday, 15 April 2019 at 13:38:33 UTC, Anton Fediushin wrote:
 This does work unless I want to use it like this:
 ```
 fun(Enum.foo);
 ---
 Error: function fun(Enum e) is not callable using argument 
 types (internal)
 cannot pass argument foo of type internal to parameter Enum e
 ```
This is correct. And you enforced this behavior as you said
 Enum.internal is private to make it inaccessible from any other 
 place. All I want is a way to have > an enum that I could 
 extend with my own methods.
So... either you pass the internals of Enum somewhere, or you don't...
Apr 15 2019
prev sibling next sibling parent reply XavierAP <n3minis-git yahoo.es> writes:
On Monday, 15 April 2019 at 08:39:24 UTC, Anton Fediushin wrote:
 Hello! I am currently trying to add a custom `toString` method
Several remarks... First of all, strings can be compared (alphabetically) as well as integers, e.g. assert("foo" > "bar") Perhaps not your use case, but worth noting. You have defined your sub-typing the opposite way that you wanted it to work: every `Enum` is an `internal`, but the other way around an `internal` may not work as an `Enum`. Your `fun` would in principle work if it were defined with an `internal` but passed an `Enum`... Of course you have defined `internal` as nested private so no... But then how did you want anything to work if no one outside Enum knows the super-type? You obviously need to re-think your problem and your design :)
 Obvious solution is to wrap an enum in a structure and utilize 
 'alias this' for subtyping like this:
Actually the obvious solution (not sure if it otherwise works for you) would be to take advantage of D's Uniform Function Call Syntax [1] and define toString as a global function that can be called as a method: enum Fubar { foo, bar } string toString(Fubar fb) { return "It works."; } void main() { import std.stdio; writeln(Fubar.foo.toString); } _________ [1] https://tour.dlang.org/tour/en/gems/uniform-function-call-syntax-ufcs
Apr 15 2019
parent reply Anton Fediushin <fediushin.anton yandex.com> writes:
On Monday, 15 April 2019 at 10:06:30 UTC, XavierAP wrote:
 On Monday, 15 April 2019 at 08:39:24 UTC, Anton Fediushin wrote:
 Hello! I am currently trying to add a custom `toString` method
Several remarks... First of all, strings can be compared (alphabetically) as well as integers, e.g. assert("foo" > "bar") Perhaps not your use case, but worth noting.
I already know that but defining enum with strings would break my code: ``` assert(Enum.foo < Enum.bar); ``` Would never succeed.
 You have defined your sub-typing the opposite way that you 
 wanted it to work: every `Enum` is an `internal`, but the other 
 way around an `internal` may not work as an `Enum`. Your `fun` 
 would in principle work if it were defined with an `internal` 
 but passed an `Enum`... Of course you have defined `internal` 
 as nested private so no... But then how did you want anything 
 to work if no one outside Enum knows the super-type?
Isn't this how subtyping works for integers and other types? For example, you have subtyped an integer and added some new methods to it?
 You obviously need to re-think your problem and your design :)
The problem here is that I want to keep methods that are related to an enum inside of this enum for purely aesthetic and organizational purposes.
 Obvious solution is to wrap an enum in a structure and utilize 
 'alias this' for subtyping like this:
Actually the obvious solution (not sure if it otherwise works for you) would be to take advantage of D's Uniform Function Call Syntax [1] and define toString as a global function that can be called as a method: enum Fubar { foo, bar } string toString(Fubar fb) { return "It works."; } void main() { import std.stdio; writeln(Fubar.foo.toString); } _________ [1] https://tour.dlang.org/tour/en/gems/uniform-function-call-syntax-ufcs
This is what I am doing now, I was just curious if there was a better solution. These global functions pollute global namespace. I know that I could put them into an own module and 'public import' just my enum because these methods would rarely be used by the other components of my application. If I would want to use them though, I'd have to import that ugly module and never forget to call `writeln(a.toString)` instead of `writeln(a)` or else it'll do not what I wanted. And once more, what I want to achieve is purely about overall code organization. I mean, if structs (data) can have functions (methods) that are performed on them, why an enum (single value) cannot have own methods performed on it?
Apr 15 2019
next sibling parent reply XavierAP <n3minis-git yahoo.es> writes:
On Monday, 15 April 2019 at 10:34:42 UTC, Anton Fediushin wrote:
 On Monday, 15 April 2019 at 10:06:30 UTC, XavierAP wrote:
 You have defined your sub-typing the opposite way that you 
 wanted it to work: every `Enum` is an `internal`, but the 
 other way around an `internal` may not work as an `Enum`. Your 
 `fun` would in principle work if it were defined with an 
 `internal` but passed an `Enum`... Of course you have defined 
 `internal` as nested private so no... But then how did you 
 want anything to work if no one outside Enum knows the 
 super-type?
Isn't this how subtyping works for integers and other types? For example, you have subtyped an integer and added some new methods to it?
Yes (leaving aside whether stuff is private or nested) but you are using the types' relationship the other way around. You have: static assert(is(Enum : internal)); But you are defining and calling fun() as if it were the other way around (internal : Enum)
Apr 15 2019
parent Anton Fediushin <fediushin.anton yandex.com> writes:
On Monday, 15 April 2019 at 12:25:38 UTC, XavierAP wrote:
 On Monday, 15 April 2019 at 10:34:42 UTC, Anton Fediushin wrote:
 On Monday, 15 April 2019 at 10:06:30 UTC, XavierAP wrote:
 [snip]
Isn't this how subtyping works for integers and other types? For example, you have subtyped an integer and added some new methods to it?
Yes (leaving aside whether stuff is private or nested) but you are using the types' relationship the other way around. You have: static assert(is(Enum : internal)); But you are defining and calling fun() as if it were the other way around (internal : Enum)
Thank you, I understand now! I think I'd have to stick with UFCS method
Apr 15 2019
prev sibling parent reply XavierAP <n3minis-git yahoo.es> writes:
On Monday, 15 April 2019 at 10:34:42 UTC, Anton Fediushin wrote:
 The problem here is that I want to keep methods that are 
 related to an enum inside of this enum for purely aesthetic and 
 organizational purposes.
 ...
 These global functions pollute global namespace.
If you have defined `x.toString` as a method, UFCS means of course you can also call `toString(x)`... So it's debatable what polluting means. More generally you insist on modules and namespaces to be different concepts, which they are (pointlessly) for C++, but not for D (purposely).
Apr 15 2019
parent XavierAP <n3minis-git yahoo.es> writes:
On Monday, 15 April 2019 at 12:38:59 UTC, XavierAP wrote:
 More generally you insist on modules and namespaces to be 
 different concepts, which they are (pointlessly) for C++, but 
 not for D (purposely).
Here I should say packages instead of modules... but the general argument stays. Anyway your design is up to you :) but sub-typing is not reflexive, in D or any language.
Apr 15 2019
prev sibling next sibling parent reply diniz <diniz posteo.net> writes:
Le 15/04/2019 à 10:39, Anton Fediushin via Digitalmars-d-learn a écrit :
 This seems to work just fine for assigning and comparisons but passing Enum as
a 
 function argument does not work:
 ```
 void fun(Enum e) {}
 
 fun(Enum.foo);
 ---
 Error: function fun(Enum e) is not callable using argument types (internal)
 Cannot pass argument foo of type internal to parameter Enum e.
 ```
I don't understand why you just don't call fun with an Enum (struct) param, since that is how fun is defined. This works by me (see call in main): struct Enum { private { enum internal { foo, bar } internal m_enum; } this (internal i) { m_enum = i; } alias m_enum this; string toString() { switch (this.m_enum) { case internal.foo : return "FOO" ; case internal.bar : return "BAR" ; default : assert(0) ; } } } void fun (Enum e) { writeln(e) ; } void main() { auto e = Enum(Enum.foo) ; fun(e) ; // -> "FOO" } [And I wouldn't make the enum (little e) private, this just risks complicating code, also eg in testing, I would just not export it.] -- diniz {la vita e estranj}
Apr 15 2019
parent Anton Fediushin <fediushin.anton yandex.com> writes:
On Monday, 15 April 2019 at 14:11:05 UTC, diniz wrote:
 Le 15/04/2019 à 10:39, Anton Fediushin via Digitalmars-d-learn 
 a écrit :
 [snip]
I don't understand why you just don't call fun with an Enum (struct) param, since that is how fun is defined. This works by me (see call in main): struct Enum { private { enum internal { foo, bar } internal m_enum; } this (internal i) { m_enum = i; } alias m_enum this; string toString() { switch (this.m_enum) { case internal.foo : return "FOO" ; case internal.bar : return "BAR" ; default : assert(0) ; } } } void fun (Enum e) { writeln(e) ; } void main() { auto e = Enum(Enum.foo) ; fun(e) ; // -> "FOO" } [And I wouldn't make the enum (little e) private, this just risks complicating code, also eg in testing, I would just not export it.]
`fun(Enum(Enum.foo));` would obviously work but `fun(Enum.foo);` would not. `Enum(Enum` is just redundant, I was looking for a solution that would make code cleaner. I don't see a problem marking internal enum as private because it isn't accessed outside of the struct
Apr 15 2019
prev sibling next sibling parent reply Alex <AJ gmail.com> writes:
On Monday, 15 April 2019 at 08:39:24 UTC, Anton Fediushin wrote:
 Hello! I am currently trying to add a custom `toString` method 
 to an enum so that:
 1. Enum members would still have numeric values and can be 
 easily compared (things like `enum a { foo = "FOO", bar = 
 "BAR”}` won't do, I want `a.foo < a.bar)`)
 2. More custom methods can be implemented in the future

 Obvious solution is to wrap an enum in a structure and utilize 
 'alias this' for subtyping like this:
 ```
 struct Enum {
   private {
     enum internal {
       foo,
       bar
     }
     internal m_enum;
   }
   this(internal i) { m_enum = i; }
   alias m_enum this;
   string toString() {
     // custom implementation of toString
   }
 }
 ```

 This seems to work just fine for assigning and comparisons but 
 passing Enum as a function argument does not work:
 ```
 void fun(Enum e) {}

 fun(Enum.foo);
 ---
 Error: function fun(Enum e) is not callable using argument 
 types (internal)
 Cannot pass argument foo of type internal to parameter Enum e.
 ```

 Of course, I could just define a bunch of functions that accept 
 my enum as the first argument and call them using UFCS but it'd 
 require to explicitly specify functions instead of D taking 
 care of that (toString() for structures is called automagically 
 by functions like writeln) and those functions would hang 
 around here and there totally unorganized. I prefer to keep 
 functions inside of structures and classes.

 If there are other ways of achieving the same *and* keeping 
 code clean and organized, please share.

 Thank you in advance,
 Anton.
yes, import std.stdio, std.meta, std.traits, std.conv; enum _MyEnum : int { a,b,c} struct _Enum(T) { T value; alias value this; // generate static field members static foreach(e, v; EnumMembers!T) { pragma(msg, "static MyEnum "~to!string(v)~" = MyEnum(T."~to!string(v)~");"); mixin("static MyEnum "~to!string(v)~" = cast(MyEnum)(T."~to!string(v)~");"); } } alias _Enum!_MyEnum MyEnum; void foo(MyEnum e) { writeln(to!int(e)); } void main() { foo(MyEnum.a); foo(MyEnum.b); foo(MyEnum.c); } https://run.dlang.io/is/WOcLrZ Note that value is never used, it just makes the cast work and treats the struct as an enum. Not sure if there is a way around that.
Apr 15 2019
parent reply Anton Fediushin <fediushin.anton yandex.com> writes:
On Monday, 15 April 2019 at 14:20:57 UTC, Alex wrote:
 On Monday, 15 April 2019 at 08:39:24 UTC, Anton Fediushin wrote:
 Hello! I am currently trying to add a custom `toString` method 
 to an enum so that:
 1. Enum members would still have numeric values and can be 
 easily compared (things like `enum a { foo = "FOO", bar = 
 "BAR”}` won't do, I want `a.foo < a.bar)`)
 2. More custom methods can be implemented in the future

 Obvious solution is to wrap an enum in a structure and utilize 
 'alias this' for subtyping like this:
 ```
 struct Enum {
   private {
     enum internal {
       foo,
       bar
     }
     internal m_enum;
   }
   this(internal i) { m_enum = i; }
   alias m_enum this;
   string toString() {
     // custom implementation of toString
   }
 }
 ```

 This seems to work just fine for assigning and comparisons but 
 passing Enum as a function argument does not work:
 ```
 void fun(Enum e) {}

 fun(Enum.foo);
 ---
 Error: function fun(Enum e) is not callable using argument 
 types (internal)
 Cannot pass argument foo of type internal to parameter Enum e.
 ```

 Of course, I could just define a bunch of functions that 
 accept my enum as the first argument and call them using UFCS 
 but it'd require to explicitly specify functions instead of D 
 taking care of that (toString() for structures is called 
 automagically by functions like writeln) and those functions 
 would hang around here and there totally unorganized. I prefer 
 to keep functions inside of structures and classes.

 If there are other ways of achieving the same *and* keeping 
 code clean and organized, please share.

 Thank you in advance,
 Anton.
yes, import std.stdio, std.meta, std.traits, std.conv; enum _MyEnum : int { a,b,c} struct _Enum(T) { T value; alias value this; // generate static field members static foreach(e, v; EnumMembers!T) { pragma(msg, "static MyEnum "~to!string(v)~" = MyEnum(T."~to!string(v)~");"); mixin("static MyEnum "~to!string(v)~" = cast(MyEnum)(T."~to!string(v)~");"); } } alias _Enum!_MyEnum MyEnum; void foo(MyEnum e) { writeln(to!int(e)); } void main() { foo(MyEnum.a); foo(MyEnum.b); foo(MyEnum.c); } https://run.dlang.io/is/WOcLrZ Note that value is never used, it just makes the cast work and treats the struct as an enum. Not sure if there is a way around that.
Thank you, this is the solution I have been looking for!
Apr 15 2019
parent Alex <AJ gmail.com> writes:
On Monday, 15 April 2019 at 20:36:09 UTC, Anton Fediushin wrote:
 On Monday, 15 April 2019 at 14:20:57 UTC, Alex wrote:
 On Monday, 15 April 2019 at 08:39:24 UTC, Anton Fediushin 
 wrote:
 Hello! I am currently trying to add a custom `toString` 
 method to an enum so that:
 1. Enum members would still have numeric values and can be 
 easily compared (things like `enum a { foo = "FOO", bar = 
 "BAR”}` won't do, I want `a.foo < a.bar)`)
 2. More custom methods can be implemented in the future

 Obvious solution is to wrap an enum in a structure and 
 utilize 'alias this' for subtyping like this:
 ```
 struct Enum {
   private {
     enum internal {
       foo,
       bar
     }
     internal m_enum;
   }
   this(internal i) { m_enum = i; }
   alias m_enum this;
   string toString() {
     // custom implementation of toString
   }
 }
 ```

 This seems to work just fine for assigning and comparisons 
 but passing Enum as a function argument does not work:
 ```
 void fun(Enum e) {}

 fun(Enum.foo);
 ---
 Error: function fun(Enum e) is not callable using argument 
 types (internal)
 Cannot pass argument foo of type internal to parameter Enum e.
 ```

 Of course, I could just define a bunch of functions that 
 accept my enum as the first argument and call them using UFCS 
 but it'd require to explicitly specify functions instead of D 
 taking care of that (toString() for structures is called 
 automagically by functions like writeln) and those functions 
 would hang around here and there totally unorganized. I 
 prefer to keep functions inside of structures and classes.

 If there are other ways of achieving the same *and* keeping 
 code clean and organized, please share.

 Thank you in advance,
 Anton.
yes, import std.stdio, std.meta, std.traits, std.conv; enum _MyEnum : int { a,b,c} struct _Enum(T) { T value; alias value this; // generate static field members static foreach(e, v; EnumMembers!T) { pragma(msg, "static MyEnum "~to!string(v)~" = MyEnum(T."~to!string(v)~");"); mixin("static MyEnum "~to!string(v)~" = cast(MyEnum)(T."~to!string(v)~");"); } } alias _Enum!_MyEnum MyEnum; void foo(MyEnum e) { writeln(to!int(e)); } void main() { foo(MyEnum.a); foo(MyEnum.b); foo(MyEnum.c); } https://run.dlang.io/is/WOcLrZ Note that value is never used, it just makes the cast work and treats the struct as an enum. Not sure if there is a way around that.
Thank you, this is the solution I have been looking for!
Yes, it is quite nice. D should simply allow enums to act as structs, they are effectively the same.[meaning they should should allow methods having methods] You might want to add a little more functionality. I screwed up the code when generalizing it, here is a bit better version: https://run.dlang.io/is/yyuy77 Using the struct you can leverage all the power of op's such as dispatching, assignment, etc. Essentially one is just using a standard struct but using enum's to define the names and values(since they are auto filled). D should just do away with enums and allow one to create a enum struct, e.g., struct S { enum : int { a,b,c } } Of which enum S : int { a,b,c } is short hand when one does not want to add new functionality or D could just treat enum like a struct by allowing methods inside the enum. The code I created essentially emulates this, one can make the enum internal and private to hide it.
Apr 15 2019
prev sibling parent Alex <AJ gmail.com> writes:
On Monday, 15 April 2019 at 08:39:24 UTC, Anton Fediushin wrote:
 Hello! I am currently trying to add a custom `toString` method 
 to an enum so that:
 1. Enum members would still have numeric values and can be 
 easily compared (things like `enum a { foo = "FOO", bar = 
 "BAR”}` won't do, I want `a.foo < a.bar)`)
 2. More custom methods can be implemented in the future

 Obvious solution is to wrap an enum in a structure and utilize 
 'alias this' for subtyping like this:
 ```
 struct Enum {
   private {
     enum internal {
       foo,
       bar
     }
     internal m_enum;
   }
   this(internal i) { m_enum = i; }
   alias m_enum this;
   string toString() {
     // custom implementation of toString
   }
 }
 ```

 This seems to work just fine for assigning and comparisons but 
 passing Enum as a function argument does not work:
 ```
 void fun(Enum e) {}

 fun(Enum.foo);
 ---
 Error: function fun(Enum e) is not callable using argument 
 types (internal)
 Cannot pass argument foo of type internal to parameter Enum e.
 ```

 Of course, I could just define a bunch of functions that accept 
 my enum as the first argument and call them using UFCS but it'd 
 require to explicitly specify functions instead of D taking 
 care of that (toString() for structures is called automagically 
 by functions like writeln) and those functions would hang 
 around here and there totally unorganized. I prefer to keep 
 functions inside of structures and classes.

 If there are other ways of achieving the same *and* keeping 
 code clean and organized, please share.

 Thank you in advance,
 Anton.
Should have been struct _Enum(T) { T value; alias value this; static foreach(e, v; EnumMembers!T) mixin("static T "~to!string(v)~" = cast(_Enum)(T."~to!string(v)~");"); }
Apr 15 2019