|
Spec-Zone .ru
спецификации, руководства, описания, API
|
Отражение обеспечивает три перечислимо-специфичных API:
Class.isEnum()Иногда необходимо динамически получить список перечислимых констант; в неотражающем коде это выполняется, вызывая неявно объявленный статический метод на перечислении. Если экземпляр перечислимого типа не доступен, единственный способ получить список возможных значений состоит в том, чтобы вызвать так как невозможно инстанцировать перечислимого типа.
Учитывая полностью определенное имя, .
import java.util.Arrays;
import static java.lang.System.out;
enum Eon { HADEAN, ARCHAEAN, PROTEROZOIC, PHANEROZOIC }
public class EnumConstants {
public static void main(String... args) {
try {
Class<?> c = (args.length == 0 ? Eon.class : Class.forName(args[0]));
out.format("Enum name: %s%nEnum constants: %s%n",
c.getName(), Arrays.asList(c.getEnumConstants()));
if (c == Eon.class)
out.format(" Eon.values(): %s%n",
Arrays.asList(Eon.values()));
// production code should handle this exception more gracefully
} catch (ClassNotFoundException x) {
x.printStackTrace();
}
}
}
Выборки вывода следуют. Ввод данных пользователем курсивом.
$ java EnumConstants java.lang.annotation.RetentionPolicy Enum name: java.lang.annotation.RetentionPolicy Enum constants: [SOURCE, CLASS, RUNTIME]
$ java EnumConstants java.util.concurrent.TimeUnit
Enum name: java.util.concurrent.TimeUnit
Enum constants: [NANOSECONDS, MICROSECONDS,
MILLISECONDS, SECONDS,
MINUTES, HOURS, DAYS]
Этот пример также показывает что значение, возвращенное идентично значению, возвращенному, вызывая values() на перечислимом типе.
$ java EnumConstants
Enum name: Eon
Enum constants: [HADEAN, ARCHAEAN,
PROTEROZOIC, PHANEROZOIC]
Eon.values(): [HADEAN, ARCHAEAN,
PROTEROZOIC, PHANEROZOIC]
Так как перечисления являются классами, другая информация может быть получена, используя те же самые API Reflection, описанные в Полях, Методах, и разделах Конструкторов этого следа. ограничить набор исследованных классов. Это также использует отличать перечислимые константы от других полей в перечислимом объявлении (не все поля являются перечислимыми константами).
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.lang.reflect.Member;
import java.util.List;
import java.util.ArrayList;
import static java.lang.System.out;
public class EnumSpy {
private static final String fmt = " %11s: %s %s%n";
public static void main(String... args) {
try {
Class<?> c = Class.forName(args[0]);
if (!c.isEnum()) {
out.format("%s is not an enum type%n", c);
return;
}
out.format("Class: %s%n", c);
Field[] flds = c.getDeclaredFields();
List<Field> cst = new ArrayList<Field>(); // enum constants
List<Field> mbr = new ArrayList<Field>(); // member fields
for (Field f : flds) {
if (f.isEnumConstant())
cst.add(f);
else
mbr.add(f);
}
if (!cst.isEmpty())
print(cst, "Constant");
if (!mbr.isEmpty())
print(mbr, "Field");
Constructor[] ctors = c.getDeclaredConstructors();
for (Constructor ctor : ctors) {
out.format(fmt, "Constructor", ctor.toGenericString(),
synthetic(ctor));
}
Method[] mths = c.getDeclaredMethods();
for (Method m : mths) {
out.format(fmt, "Method", m.toGenericString(),
synthetic(m));
}
// production code should handle this exception more gracefully
} catch (ClassNotFoundException x) {
x.printStackTrace();
}
}
private static void print(List<Field> lst, String s) {
for (Field f : lst) {
out.format(fmt, s, f.toGenericString(), synthetic(f));
}
}
private static String synthetic(Member m) {
return (m.isSynthetic() ? "[ synthetic ]" : "");
}
}
$ java EnumSpy java.lang.annotation.RetentionPolicy
Class: class java.lang.annotation.RetentionPolicy
Constant: public static final java.lang.annotation.RetentionPolicy
java.lang.annotation.RetentionPolicy.SOURCE
Constant: public static final java.lang.annotation.RetentionPolicy
java.lang.annotation.RetentionPolicy.CLASS
Constant: public static final java.lang.annotation.RetentionPolicy
java.lang.annotation.RetentionPolicy.RUNTIME
Field: private static final java.lang.annotation.RetentionPolicy[]
java.lang.annotation.RetentionPolicy. [ synthetic ]
Constructor: private java.lang.annotation.RetentionPolicy()
Method: public static java.lang.annotation.RetentionPolicy[]
java.lang.annotation.RetentionPolicy.values()
Method: public static java.lang.annotation.RetentionPolicy
java.lang.annotation.RetentionPolicy.valueOf(java.lang.String)
Вывод показывает то объявление только содержит три перечислимых константы. Перечислимые константы представляются как public static final поля. Поле, конструктор, и методы являются сгенерированным компилятором. $VALUES поле связывается с реализацией values() метод.
Вывод для шоу так намного больше сложных перечислений возможны. Этот class включает несколько методов так же как дополнительных объявленных полей static final которые не являются перечислимыми константами.
$ java EnumSpy java.util.concurrent.TimeUnit
Class: class java.util.concurrent.TimeUnit
Constant: public static final java.util.concurrent.TimeUnit
java.util.concurrent.TimeUnit.NANOSECONDS
Constant: public static final java.util.concurrent.TimeUnit
java.util.concurrent.TimeUnit.MICROSECONDS
Constant: public static final java.util.concurrent.TimeUnit
java.util.concurrent.TimeUnit.MILLISECONDS
Constant: public static final java.util.concurrent.TimeUnit
java.util.concurrent.TimeUnit.SECONDS
Constant: public static final java.util.concurrent.TimeUnit
java.util.concurrent.TimeUnit.MINUTES
Constant: public static final java.util.concurrent.TimeUnit
java.util.concurrent.TimeUnit.HOURS
Constant: public static final java.util.concurrent.TimeUnit
java.util.concurrent.TimeUnit.DAYS
Field: static final long java.util.concurrent.TimeUnit.C0
Field: static final long java.util.concurrent.TimeUnit.C1
Field: static final long java.util.concurrent.TimeUnit.C2
Field: static final long java.util.concurrent.TimeUnit.C3
Field: static final long java.util.concurrent.TimeUnit.C4
Field: static final long java.util.concurrent.TimeUnit.C5
Field: static final long java.util.concurrent.TimeUnit.C6
Field: static final long java.util.concurrent.TimeUnit.MAX
Field: private static final java.util.concurrent.TimeUnit[]
java.util.concurrent.TimeUnit. [ synthetic ]
Constructor: private java.util.concurrent.TimeUnit()
Constructor: java.util.concurrent.TimeUnit
(java.lang.String,int,java.util.concurrent.TimeUnit)
[ synthetic ]
Method: public static java.util.concurrent.TimeUnit
java.util.concurrent.TimeUnit.valueOf(java.lang.String)
Method: public static java.util.concurrent.TimeUnit[]
java.util.concurrent.TimeUnit.values()
Method: public void java.util.concurrent.TimeUnit.sleep(long)
throws java.lang.InterruptedException
Method: public long java.util.concurrent.TimeUnit.toNanos(long)
Method: public long java.util.concurrent.TimeUnit.convert
(long,java.util.concurrent.TimeUnit)
Method: abstract int java.util.concurrent.TimeUnit.excessNanos
(long,long)
Method: public void java.util.concurrent.TimeUnit.timedJoin
(java.lang.Thread,long) throws java.lang.InterruptedException
Method: public void java.util.concurrent.TimeUnit.timedWait
(java.lang.Object,long) throws java.lang.InterruptedException
Method: public long java.util.concurrent.TimeUnit.toDays(long)
Method: public long java.util.concurrent.TimeUnit.toHours(long)
Method: public long java.util.concurrent.TimeUnit.toMicros(long)
Method: public long java.util.concurrent.TimeUnit.toMillis(long)
Method: public long java.util.concurrent.TimeUnit.toMinutes(long)
Method: public long java.util.concurrent.TimeUnit.toSeconds(long)
Method: static long java.util.concurrent.TimeUnit.x(long,long,long)