Функция, возвращающая имя класса В D

скажем,классы A1, A2,...Всего расширяет абстрактный класс Б. Я бы хотел A1,...,Это иметь функцию, которая возвращает строку имени класса. Это, конечно, известно во время компиляции, но я хотел бы реализовать эту функцию в B, и используйте наследование, чтобы все Ai: s получили эту функциональность.

в java это можно легко сделать, позволив B иметь метод

String getName() {
    return this.getClass();
}

больше или меньше. Итак, как мне это сделать в D? Кроме того, есть ли способ, используя черты или аналогично, чтобы определить, какие члены класса являются открытыми?

3 ответов


просто typeof(this).stringof

однако это исправлено во время компиляции, поэтому наследование не изменяет значение

this.typeinfo.name

даст динамическое имя classname экземпляра

http://www.d-programming-language.org/expression.html#typeidexpression
http://www.d-programming-language.org/phobos/object.html#TypeInfo_Class


известно во время компиляции, но оценки имя класса во время выполнения требует demangling, я думаю.

вот если оценка времени выполнения в порядке:

import std.stdio;
import std.algorithm;

abstract class B {
    string className() @property {
        return this.classinfo.name.findSplit(".")[2];
    }
}

class A1 : B { }
class A2 : B { }

void main()
{
    auto a1 = new A1();
    writeln(a1.className);

    auto a2 = new A2();
    writeln(a2.className);
}

вы можете получить имя класса, просто используя ClassName.stringof.

Если вы хотите его в качестве виртуальной функции, я бы рекомендовал использовать Любопытно Повторяющийся Шаблон Шаблон:

class B
{
    abstract string getName();
}

class BImpl(T)
{
    string getName() { return T.stringof; }
}

class A1 : BImpl!A1 { ... }
class A2 : BImpl!A2 { ... }
/+ etc. +/

к сожалению, на данный момент нет способа определить, какие члены класса являются общедоступными. Вы можете выполнить итерацию всех членов с помощью аналогичный allmembers черта.

foreach (member; __traits(allMembers, MyClass))
    writeln(member);