Are there metaclasses or class reference in D?
D 中是否有任何类引用系统?为了更准确,我寻找相当于 Delphi
1 | TMyClassRef = class of TMyClass; |
这将用于工厂(就像在
1 2 3 4 5 | // ideally void AddNew(*TBaseClass APtr, /*?class_ref_type?*/ AClassType) { *APtr = new AClassType; } |
目前我这样做:
1 2 3 4 | void AddNew(*TBaseClass APtr) { *APtr = new typeof(*APtr); } |
但问题是
也许我完全错过了 Delphi 中的想法,但这似乎是模板的用途:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 | import std.stdio; class Parent { string inherited() { return"Hello from parent"; } override string toString() { return"Hello from parent"; } } class Child : Parent { override string toString() { return"Hello from child"; } } void add(C, P)(P* ptr) { *ptr = new C; } void main() { Parent t; writeln(t); // prints null add!Child(&t); writeln(t); // prints Hello from child writeln(t.inherited()); // prints Hello from parent } |
这样你传入你想要实例化的类型而不是那个类型的实例化对象。如果 C 不是 add().
中 P 的子级,这应该会产生编译错误
编辑:
如果你想更具体地使用 add,你可以这样做:
1 2 3 | void add(T : Parent)(Parent* ptr) { *ptr = new T; } |
为了让事情变得更好,使用
1 2 3 4 5 6 7 | void add(T : Parent)(out Parent ptr) { ptr = new T; } void main() { Parent p; add!Child(p); } |
就我所理解的 Delphi 概念而言,D 没有 Delphi 方式的类引用。如果您需要对对象构造做出运行时决定,
您可以通过
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 | import std.stdio; class Base { void f() { writeln("Base"); } } class Descendant : Base { override void f() { writeln("Descendant"); } } Base makeNew(Base other) { // cast is needed because create() returns plain Object // we can be sure it is Base at least, though, because it was crated from Base return cast(Base)typeid(other).create(); } void main() { Descendant source = new Descendant; Base target = makeNew(source); // prints"Descendant" target.f(); } |
此代码示例是否与您想要的相似?
D 通常在运行时操作和编译时操作之间有非常明显的区别。