Walter Bright wrote:
I mean there is modifiable-at-runtime, instance-specific data.
In C#, no there isn't. Attributes are simply objects constructed
(when gotten) from an Entity's metadata. No memory is stored
per-instance unless you manage the objects manually:
class A : Attribute { public string s = "Default"; }
[TestA] class C {}
static void Main()
{
// The line below is equivalent to: var a = new A();
// except that it's construction is defined by
// metadata stored in type C.
var a = typeof(C).GetCustomAttributes(true)[0] as A;
a.s = "Modification";
Console.WriteLine(a.s); // prints "Modification"
// Therefor...
var b = typeof(C).GetCustomAttributes(true)[0] as A;
Console.WriteLine(b.s); // prints "Default"
}
In that case, there's two
benefits I can think of over "traditional" member data:
Instance memory
(attributes are create at reflection),
Lazy initialization is a standard pattern. No special language
features are needed for it.
I see how my statements (and code examples) where confusing. I
meant that no attribute data is stored per-instance at all
(unless traditionally done so), and that attribute objects are
simply create in-place at the point of access. So to clarify my
previous code a bit:
attribute class A { string i = "Default"; }
@A class C { A a; }
void main()
{
auto a = C@A; // create new A based on C
assert(is(typeof(a) : A));
// alternatively you could do:
auto c = new C();
auto a = c@A; // same as: typeof(c)@A
c.a = c@A; // explicitly store attribute
}
Note: Might want to use the "new" keyword with class type
attributes (auto a = new C@A), but the idea's there. Plus, I
think that looks a lot better than the C# version.
and reusable metadata packages (similar
to how you might use mixin templates only with less noise and
reflection capabilities).
Sounds like a garden variety user-defined data type.
It is. Only it's a data type who's construction values are stored
in metadata (per entity), and therefor can be used at both
compile and run times. By per-entity I mean for each unique Type,
Type member, Sub-Type, etc.
I don't know of any existing D idiom that is capable of what I
presented. If there is, I would like to know. Here's the closest
I can think of:
mixin template CoolInt(bool cool, string name)
{
mixin("enum bool " ~ name ~ "_isCool = cool;");
mixin("int " ~ name ~ ";");
}
class CoolClass
{
mixin CoolInt!(true, "a");
mixin CoolInt!(false, "b");
}
void main()
{
auto c = new CoolClass();
writeln(c.a_isCool); // true
writeln(c.b_isCool); // false
}
which, aside from noise, is great for runtime reflection, but
it's completely useless (i think) for the compiler because the
variables are created through arbitrary strings. Plus, I don't
know how you'd store anything but simple variables, which more
complex data would require a lot of <entity>_variables.