Как узнать имя класса
Перейти к содержимому

Как узнать имя класса

Получение имени класса экземпляра?

Как узнать имя класса, который создал экземпляр объекта в Python, если функция, из которой я делаю это, является базовым классом, из которого был получен класс экземпляра?

Думал, может быть, модуль проверки может иметь помог мне здесь, но это не дает мне то, что я хочу. И если не считать синтаксического анализа члена __class__ , я не уверен, как получить эту информацию.

8 ответов

Вы пробовали атрибут __name__ класса? то есть type(x).__name__ даст вам имя класса, который, я думаю, вам нужен.

Этот метод работает только с классами нового стиля. Ваш код может использовать классы старого стиля. Следующее работает для обоих:

В качестве альтернативы вы можете использовать декоратор classmethod :

Вы хотите имя класса в виде строки?

Вот простой пример, основанный на GHZ, который может кому-то помочь:

Помимо захвата специального __name__ атрибута, вы может понадобиться квалифицированное имя для данного класса / функции. Это делается путем захвата типов __qualname__ .

В большинстве случаев они будут точно такими же, но при работе с вложенными классами / методами они отличаются в выводе, который вы получаете. Например:

Поскольку вам нужен самонаблюдение, вы всегда можете об этом подумать.

Приведенный выше пример кода (при вводе в интерактивном интерпретаторе) будет производить ‘__main__.A’ , а не ‘A’ , который создается, если вызывается атрибут __name__ . Просто передавая результат A.__class__ в конструктор str , анализ обрабатывается для вас. Тем не менее, вы также можете использовать следующий код, если вы хотите что-то более явное.

Такое поведение может быть предпочтительным, если у вас есть классы с одинаковыми именами, определенные в отдельных модулях.

Приведенный выше пример кода был протестирован в Python 2.7.5.

Узнать имя класса во время исполнения программы

У меня есть функция (используется для записи логов), которая вызывается в разных классах. Не хочется каждый раз переписывать код в ней для каждого нового класса(они будут и добавляться и убираться со временем, ну или вообще функция будет использоваться в дальнейшем в других проектах).

Мне хотелось бы узнавать имя класса, из которого она вызывается (для задания имени файлу и прочих плюшек) не передавая лишних параметров в функцию.

Это можно реализовать? Можно и boost`ом.

Функция typeid(object) возвращает объект типа type_info с информацией о типе объекта, для которого она вызывается (собственно, о классе). У этого объекта( type_info ) есть метод name() , который и возвращает имя класса. Для использования нужно подключить <typeinfo> .

Так что в итоге для получения имени класса нужно использовать

Или, если функция не является методом класса, передать в typeid сам объект или разыменованный указатель.

user avatar

Собственные средства c++ не позволяют ничего узнать о контектсте вызова функции.

Стек вызова можно проанализировать с помощью некоторых внешних библиотек / API операционной системы. Например: http://man7.org/linux/man-pages/man3/backtrace.3.html https://msdn.microsoft.com/en-us/library/ms680650%28VS.85%29.aspx . Но для применение этих средств может налагать дополнительные ограничения на собираемый код (сборка с отладочной информацией и т.д.).

Более разумно, ИМХО, передавать контекст вызова явно: это позволит использовать «штатные» средства c++: __FILE__ , __LINE__ , __func__ , . Извлечение контекста можно замаскировать макросом:

Имя класса можно извлечь либо разобрав имя __FUNCTION__ , либо из указателя this :

Но не хочется включать этот обращение к this в макрос, поскольку функции может быть вызвана из контекста, статической функции.

С другой стороны для целей разделения логов может быть достаточно __FILE__ .

Получение имени класса в Java

Изучите различные способы получения имени класса в Java.

  • Автор записи

1. Обзор

В этом уроке мы узнаем о четырех способах извлечения имени класса из методов Class API: getSimpleName () , getName () , getTypeName() и getCanonicalName() .

Эти методы могут сбивать с толку из-за их схожих названий и их несколько расплывчатых Javadoc. Они также имеют некоторые нюансы, когда речь заходит о примитивных типах, типах объектов, внутренних или анонимных классах и массивах.

2. Получение Простого Имени

Давайте начнем с метода getSimpleName () .

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

Как следует из его названия, getSimpleName() возвращает простое имя базового класса, то есть имя, которое было дано в исходном коде .

Давайте представим себе следующий класс:

Его простое имя будет RetrieveClassName :

Мы также можем получить примитивные типы и массивы простых имен. Для примитивных типов, которые будут просто их именами, например int, boolean или float .

А для массивов метод вернет простое имя типа массива, за которым следует пара открывающих и закрывающих скобок для каждого измерения массива ([]) :

Следовательно, для двумерного String массива вызов getSimpleName() в его классе вернет String[][] .

Наконец, есть конкретный случай анонимных классов. Вызов getSimpleName() в анонимном классе вернет пустую строку.

3. Получение Других Имен

Теперь пришло время взглянуть на то, как мы могли бы получить имя класса, имя типа или каноническое имя. В отличие от getSimpleName() , эти имена предназначены для предоставления дополнительной информации о классе.

Метод getCanonicalName() всегда возвращает каноническое имя , определенное в спецификации языка Java .

Что касается других методов, выходные данные могут немного отличаться в зависимости от вариантов использования. Мы увидим, что это означает для различных типов примитивов и объектов.

3.1. Примитивные типы

Давайте начнем с примитивных типов, поскольку они просты. Для примитивных типов все три метода getName (), getTypeName() и getCanonicalName() вернут тот же результат, что и getSimpleName() :

3.2. Типы объектов

Теперь мы посмотрим, как эти методы работают с типами объектов. Их поведение, как правило, одинаковое: все они возвращают каноническое имя класса .

В большинстве случаев это полное имя, которое содержит все простые имена пакетов классов, а также простое имя класса:

3.3. Внутренние классы

То, что мы видели в предыдущем разделе, – это общее поведение этих вызовов методов, но есть несколько исключений.

Внутренние классы-один из них. Методы getName() и getTypeName() ведут себя иначе, чем метод getCanonicalName() для внутренних классов.

getCanonicalName() по-прежнему возвращает каноническое имя класса , то есть каноническое имя заключающего класса плюс простое имя внутреннего класса, разделенное точкой.

С другой стороны, методы getName() и getTypeName() возвращают почти то же самое, но используют доллар в качестве разделителя между каноническим именем заключающего класса и простым именем внутреннего класса .

Давайте представим себе внутренний класс InnerClass нашего RetrieveClassName :

Затем каждый вызов обозначает внутренний класс немного по-другому:

3.4. Анонимные классы

Анонимные классы-еще одно исключение.

Как мы уже видели, у них нет простого имени, но у них также нет канонического имени . Поэтому getCanonicalName() ничего не возвращает. В отличие от getSimpleName() , getCanonicalName() вернет null | и не пустую строку при вызове анонимного класса.

Что касается getName() и getTypeName () , они вернут каноническое имя вызывающего класса, за которым последуют доллар и число, представляющее положение анонимного класса среди всех анонимных классов, созданных в вызывающем классе .

Давайте проиллюстрируем это на примере. Мы создадим здесь два анонимных класса и вызовем getName() на первом и getTypeName() на втором, объявив их в com.baeldung.Главная :

Следует отметить, что второй вызов возвращает имя с увеличенным числом в конце, поскольку оно применяется ко второму анонимному классу.

3.5. Массивы

Наконец, давайте посмотрим, как массивы обрабатываются вышеперечисленными тремя методами.

Чтобы указать, что мы имеем дело с массивами, каждый метод обновит свой стандартный результат. Методы getTypeName() и getCanonicalName() добавят пары скобок к своему результату.

Давайте рассмотрим следующий пример, в котором мы вызываем getTypeName() и getCanonicalName() для двумерного внутреннего класса массива:

Обратите внимание, как первый вызов использует доллар вместо точки, чтобы отделить внутреннюю часть класса от остальной части имени.

Теперь давайте посмотрим, как работает метод getName () . При вызове массива примитивного типа он возвращает открывающую скобку и букву, представляющую примитивный тип . Давайте проверим это на следующем примере, вызвав этот метод для двумерного массива примитивных целых чисел:

С другой стороны, при вызове массива объектов он добавит открывающую скобку и букву L к своему стандартному результату и завершится точкой с запятой . Давайте попробуем это на массиве RetrieveClassName :

4. Заключение

В этой статье мы рассмотрели четыре метода доступа к имени класса в Java. Эти методы: getSimpleName(), getName(), getTypeName() и getCanonicalName() .

Мы узнали, что первый просто возвращает имя исходного кода класса, в то время как другие предоставляют дополнительную информацию, такую как имя пакета и указание на то, является ли класс внутренним или анонимным классом.

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *