On Fri, Feb 26, 2021 at 11:37:18AM -0800, H. S. Teoh via Digitalmars-d-learn wrote: > On Wed, Feb 24, 2021 at 08:10:30PM +0000, Mike Brown via Digitalmars-d-learn > wrote: > [...] > > Thank you for the reply. Im struggling extending this to get the > > nesting working. [...]
Alright, here's an actual working example. Instead of using classes, I decided to use templates instead, but the underlying concept is the same: -------------------------------------snip-------------------------------------- template branch(string _ident, _values...) { enum ident = _ident; alias values = _values; } // I used strings for easier concatenation to code, otherwise we have to use // std.conv to convert it which is slow in CTFE. static immutable string[] primes = [ "2", "3", "5", "7", "11", "13", "17", "19", "23", "29", "31", "37", "41", // fill in more if you need to ]; string genPrimeId(size_t[] indices) in (indices.length > 0) { string result = primes[indices[0]]; foreach (i; indices[1 .. $]) { result ~= "*" ~ primes[i]; } return result; } template primeIdsImpl(size_t[] indices, Args...) if (indices.length > 0 && Args.length > 0) { static if (Args.length == 1) { static if (is(typeof(Args[0]) == string)) { enum primeIdsImpl = Args[0] ~ "=" ~ genPrimeId(indices) ~ ",\n"; } else { enum primeIdsImpl = Args[0].ident ~ "=" ~ genPrimeId(indices) ~ ",\n" ~ primeIdsImpl!(indices ~ [ indices[$-1] + 1 ], Args[0].values); } } else { enum primeIdsImpl = primeIdsImpl!(indices, Args[0]) ~ primeIdsImpl!(indices[0 .. $-1] ~ [ indices[$-1] + 1 ], Args[1 .. $]); } } template primeIds(string enumName, Args...) if (Args.length > 0) { enum primeIds = "enum " ~ enumName ~ " {\n" ~ primeIdsImpl!([0], Args) ~ "}"; } mixin(primeIds!("token_type", "endOfFile", "unknown", "newline", branch!("identifier", "userDefined", "var", "uses", "constructor", "do_", "end_", ), branch!("operator", "copyAssignment", ), )); void main() { import std; writefln("%s", token_type.identifier); writefln("%d", token_type.identifier); } -------------------------------------snip-------------------------------------- You can change the mixin line to `pragma(msg, ...)` instead to see the generated code string. I noticed that the definitions of the first nested identifiers are different from your original post; I don't know if this is a misunderstanding on my side or an oversight on your part? After identifier=7, the next prime should be 11, not 13, so userDefined should start with 11*identifier rather than 13*identifier. T -- Shin: (n.) A device for finding furniture in the dark.