digitalmars.D - Fun with allMembers
- Shin Fujishiro <rsinfu gmail.com> May 13 2009
- Sam Hu <samhudotsamhu gmail.com> May 13 2009
- Sam Hu <samhudotsamhu gmail.com> May 13 2009
- Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> May 14 2009
- Lutger <lutger.blijdestijn gmail.com> May 14 2009
- Georg Wrede <georg.wrede iki.fi> May 14 2009
- Shin Fujishiro <rsinfu gmail.com> May 14 2009
- "Denis Koroskin" <2korden gmail.com> May 14 2009
- "Denis Koroskin" <2korden gmail.com> May 14 2009
- Shin Fujishiro <rsinfu gmail.com> May 14 2009
- Shin Fujishiro <rsinfu gmail.com> May 14 2009
Hi,
I've had fun with the allMembers traits over the past few days and found
it more powerful than I thought.
__traits(allMembers, T) returns the member names of T. As some might
already know, T is not restricted to a class or struct; it can also be
an enum, template, or even module. Try this:
--------------------
enum E { a, b, c }
template T() { int x, y, z; }
import std.stdio;
pragma(msg, __traits(allMembers, E).stringof);
pragma(msg, __traits(allMembers, T).stringof);
pragma(msg, __traits(allMembers, std.stdio).stringof);
--------------------
You'll like the result :). It must be usable!
For example, using allMembers with enums, I could implement
enumToString and enumFromString without defineEnum.
Code: http://codepad.org/HVvPjoI7
So, what other uses could there be?
May 13 2009
Powerful ...but in my pc the output is : ["a","b","c"] ["x","y"] //====>not ["x","y","z"]??? ["object","core",...]
May 13 2009
Shin Fujishiro wrote:Hi, I've had fun with the allMembers traits over the past few days and found it more powerful than I thought. __traits(allMembers, T) returns the member names of T. As some might already know, T is not restricted to a class or struct; it can also be an enum, template, or even module. Try this: -------------------- enum E { a, b, c } template T() { int x, y, z; } import std.stdio; pragma(msg, __traits(allMembers, E).stringof); pragma(msg, __traits(allMembers, T).stringof); pragma(msg, __traits(allMembers, std.stdio).stringof); -------------------- You'll like the result :). It must be usable! For example, using allMembers with enums, I could implement enumToString and enumFromString without defineEnum. Code: http://codepad.org/HVvPjoI7 So, what other uses could there be?
Wow, I didn't know about this! It might as well be everything needed for a full-blown compile-time reflection package! To answer your question: for starters, try to implement BlackHole and WhiteHole as explained here: http://erdani.dreamhosters.com/cranking-policies-up.pdf Andrei
May 14 2009
Andrei Alexandrescu wrote:Shin Fujishiro wrote:Hi, I've had fun with the allMembers traits over the past few days and found it more powerful than I thought. __traits(allMembers, T) returns the member names of T. As some might already know, T is not restricted to a class or struct; it can also be an enum, template, or even module. Try this: -------------------- enum E { a, b, c } template T() { int x, y, z; } import std.stdio; pragma(msg, __traits(allMembers, E).stringof); pragma(msg, __traits(allMembers, T).stringof); pragma(msg, __traits(allMembers, std.stdio).stringof); -------------------- You'll like the result :). It must be usable! For example, using allMembers with enums, I could implement enumToString and enumFromString without defineEnum. Code: http://codepad.org/HVvPjoI7 So, what other uses could there be?
Wow, I didn't know about this! It might as well be everything needed for a full-blown compile-time reflection package! To answer your question: for starters, try to implement BlackHole and WhiteHole as explained here: http://erdani.dreamhosters.com/cranking-policies-up.pdf Andrei
See also this article from the author of PyD: http://kirkmcdonald.blogspot.com/2007/07/inadequacies-of-traits.html (Not that it isn't very powerful as is.)
May 14 2009
Andrei Alexandrescu wrote:Shin Fujishiro wrote:Hi, I've had fun with the allMembers traits over the past few days and found it more powerful than I thought. __traits(allMembers, T) returns the member names of T. As some might already know, T is not restricted to a class or struct; it can also be an enum, template, or even module. Try this: -------------------- enum E { a, b, c } template T() { int x, y, z; } import std.stdio; pragma(msg, __traits(allMembers, E).stringof); pragma(msg, __traits(allMembers, T).stringof); pragma(msg, __traits(allMembers, std.stdio).stringof); -------------------- You'll like the result :). It must be usable! For example, using allMembers with enums, I could implement enumToString and enumFromString without defineEnum. Code: http://codepad.org/HVvPjoI7 So, what other uses could there be?
Wow, I didn't know about this! It might as well be everything needed for a full-blown compile-time reflection package! To answer your question: for starters, try to implement BlackHole and WhiteHole as explained here: http://erdani.dreamhosters.com/cranking-policies-up.pdf
First of all, congratulations for conjuring up a cool (and marketing-savvy name) for a concept!!! Suppose I decide to use BlackHole as a base class. Would that mean that I create the base class like class RichardNixon createBlackHoleClass!() class DerivedRN : RichardNixon { /* something declared here, makes no difference in this example */ int foo(int ip) {/* whatever */} } and then, I'd expect it to work like void main() { DerivedRN drn = new DerivedRN; float ivar, jvar; jvar = drn.bar(ivar); // note: bar, not foo } and it'd work like RichardNixon were actually defined as class RichardNixon { float bar(float jv) { return float 0; } // or whatever }
May 14 2009
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote:To answer your question: for starters, try to implement BlackHole and WhiteHole as explained here: http://erdani.dreamhosters.com/cranking-policies-up.pdf
Ah, I've hand-written such BlackHoles number of times :). I thought I could implement a template which automatically generates such code, but some weird behaviors of the __traits(getVirtualFunctions) blocked me from implementing it. Anyway, I'll try to implement them again. Thanks!
May 14 2009
On Thu, 14 May 2009 07:22:54 +0400, Shin Fujishiro <rsinfu gmail.com> wrote:Hi, I've had fun with the allMembers traits over the past few days and found it more powerful than I thought. __traits(allMembers, T) returns the member names of T. As some might already know, T is not restricted to a class or struct; it can also be an enum, template, or even module. Try this: -------------------- enum E { a, b, c } template T() { int x, y, z; } import std.stdio; pragma(msg, __traits(allMembers, E).stringof); pragma(msg, __traits(allMembers, T).stringof); pragma(msg, __traits(allMembers, std.stdio).stringof); -------------------- You'll like the result :). It must be usable! For example, using allMembers with enums, I could implement enumToString and enumFromString without defineEnum. Code: http://codepad.org/HVvPjoI7 So, what other uses could there be?
Great, now the following is possible with your code: string toString(Enum)(Enum e) if (is(Enum == enum)) { return enumToString(e); } assert("RED" == toString(c)); // and, once implemented: assert("RED" == c.toString()); Although returning "Color.RED" might be better, but it's really not a problem. Is there any way your code could be contributed to Phobos?
May 14 2009
On Thu, 14 May 2009 19:24:23 +0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote:Shin Fujishiro wrote:Hi, I've had fun with the allMembers traits over the past few days and found it more powerful than I thought. __traits(allMembers, T) returns the member names of T. As some might already know, T is not restricted to a class or struct; it can also be an enum, template, or even module. Try this: -------------------- enum E { a, b, c } template T() { int x, y, z; } import std.stdio; pragma(msg, __traits(allMembers, E).stringof); pragma(msg, __traits(allMembers, T).stringof); pragma(msg, __traits(allMembers, std.stdio).stringof); -------------------- You'll like the result :). It must be usable! For example, using allMembers with enums, I could implement enumToString and enumFromString without defineEnum. Code: http://codepad.org/HVvPjoI7 So, what other uses could there be?
Wow, I didn't know about this! It might as well be everything needed for a full-blown compile-time reflection package! To answer your question: for starters, try to implement BlackHole and WhiteHole as explained here: http://erdani.dreamhosters.com/cranking-policies-up.pdf Andrei
I wonder why it says "No popular compiled language offers both" about CT introspection and code generation?
May 14 2009
Another example of allMembers: Generalized selective import.
--------------------
template isUnaryRealFunction(alias sym)
{
enum isUnaryRealFunction = is(typeof(sym(0.L)) == real);
}
// import unary real functions from std.math
mixin importOnly!("std.math", isUnaryRealFunction);
// unary real functions are imported
static assert(__traits(compiles, abs, sqrt, sin));
// pow is not since it's a binary function
static assert(!__traits(compiles, pow));
--------------------
Full code: http://codepad.org/lc57IKIz
A template importOnly imports only symbols satisfying a predicate
template. I don't know if it's actually useful or not, but it shows the
potential of D's compile-time reflection. Seems we can do everything!
May 14 2009
"Denis Koroskin" <2korden gmail.com> wrote:Great, now the following is possible with your code: string toString(Enum)(Enum e) if (is(Enum == enum)) { return enumToString(e); } assert("RED" == toString(c)); // and, once implemented: assert("RED" == c.toString()); Although returning "Color.RED" might be better, but it's really not a problem. Is there any way your code could be contributed to Phobos?
Sure. I think it can be merged into std.conv.to.
May 14 2009









Sam Hu <samhudotsamhu gmail.com> 