logo

API за отражение на Java

Java Reflection е процес на изследване или модифициране на поведението на даден клас по време на изпълнение .

The java.lang.Class клас предоставя много методи, които могат да се използват за получаване на метаданни, изследване и промяна на поведението на даден клас по време на изпълнение.

Пакетите java.lang и java.lang.reflect предоставят класове за отражение на java.

Къде се използва

API Reflection се използва главно в:

  • IDE (интегрирана среда за разработка) напр. Eclipse, MyEclipse, NetBeans и др.
  • Дебъгер
  • Инструменти за тестване и др.
Знаеш ли?
  • По колко начина можем да получим екземпляра на класа Class?
  • Как да създадете инструмента javap?
  • Как да създадете инструмента appletviewer?
  • Как да получите достъп до частния метод извън класа?

java.lang.Class клас

Класът java.lang.Class изпълнява основно две задачи:

  • предоставя методи за получаване на метаданните на клас по време на изпълнение.
  • предоставя методи за изследване и промяна на поведението на даден клас по време на изпълнение.

Често използвани методи на клас клас:

МетодОписание
1) публичен низ getName()връща името на класа
2) публичен статичен клас forName(String className) хвърля ClassNotFoundExceptionзарежда класа и връща препратката към клас клас.
3) public Object newInstance() хвърля InstantiationException, IllegalAccessExceptionсъздава нов екземпляр.
4) публичен булев isInterface()проверява дали е интерфейс.
5) публичен булев isArray();проверява дали е масив.
6) публичен булев isPrimitive()проверява дали е примитивен.
7) публичен клас getSuperclass()връща препратката към клас суперклас.
8) public Field[] getDeclaredFields() хвърля SecurityExceptionвръща общия брой полета от този клас.
9) публичен метод [] getDeclaredMethods() хвърля SecurityExceptionвръща общия брой методи от този клас.
10) public Constructor[] getDeclaredConstructors() хвърля SecurityExceptionвръща общия брой конструктори от този клас.
11) публичен метод getDeclaredMethod(Име на низ,Class[] parameterTypes) хвърля NoSuchMethodException,SecurityExceptionвръща екземпляра на клас метод.

Как да получа обекта на класа Class?

Има 3 начина да получите екземпляра на класа Class. Те са както следва:

  • forName() метод на клас Class
  • метод getClass() на клас Object
  • синтаксисът .class

1) forName() метод на клас Class

  • се използва за динамично зареждане на класа.
  • връща екземпляра на клас клас.
  • Трябва да се използва, ако знаете пълното име на класа. Това не може да се използва за примитивни типове.

Нека видим простия пример за метод forName().

средно срещу средно

Име на файл: Test.java

 class Simple{} public class Test{ public static void main(String args[]) throws Exception { Class c=Class.forName('Simple'); System.out.println(c.getName()); } } 

Изход:

 Simple 

2) метод getClass() на клас Object

Той връща екземпляра на клас клас. Трябва да се използва, ако знаете вида. Освен това може да се използва с примитиви.

Име на файл: Test.java

 class Simple{} class Test{ void printName(Object obj){ Class c=obj.getClass(); System.out.println(c.getName()); } public static void main(String args[]){ Simple s=new Simple(); Test t=new Test(); t.printName(s); } } 

Изход:

Simple 

3) Синтаксисът .class

Ако даден тип е наличен, но няма екземпляр, тогава е възможно да се получи клас чрез добавяне на '.class' към името на типа. Може да се използва и за примитивни типове данни.

Име на файл: Test.java

 class Test{ public static void main(String args[]){ Class c = boolean.class; System.out.println(c.getName()); Class c2 = Test.class; System.out.println(c2.getName()); } } 

Изход:

 boolean Test 

Определяне на обекта на класа

Следните методи на клас клас се използват за определяне на обекта на класа:

1) публичен булев isInterface(): определя дали посоченият обект Class представлява тип интерфейс.

2) публичен булев isArray(): определя дали този обект Class представлява клас масив.

3) публичен булев isPrimitive(): определя дали посоченият обект Class представлява примитивен тип.

Нека видим простия пример за API за отражение, за да определим типа обект.

Име на файл: Test.java

 class Simple{} interface My{} class Test{ public static void main(String args[]){ try{ Class c=Class.forName('Simple'); System.out.println(c.isInterface()); Class c2=Class.forName('My'); System.out.println(c2.isInterface()); }catch(Exception e){System.out.println(e);} } } 

Изход:

 false true 

Плюсове и минуси на отражението

Отражението на Java винаги трябва да се използва с повишено внимание. Въпреки че отражението предоставя много предимства, то има и някои недостатъци. Нека първо обсъдим предимствата.

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

java стекове

Минуси: Използвайки отражение, човек може да наруши принципите на капсулирането. Възможно е достъп до частните методи и полета на клас чрез отражение. По този начин отражението може да изтече важни данни към външния свят, което е опасно. Например, ако някой получи достъп до частните членове на клас и му зададе нулева стойност, тогава другият потребител от същия клас може да получи NullReferenceException и това поведение не се очаква.

Друг недостатък е режийното представяне. Тъй като типовете в отражението се разрешават динамично, JVM (Java Virtual Machine) оптимизация не може да се извърши. Следователно операциите, извършвани от отражения, обикновено са бавни.

Заключение

Поради гореспоменатите недостатъци обикновено е препоръчително да избягвате използването на отражение. Това е разширена функция, която трябва да се използва само от програмисти или разработчици, които имат добри познания по основи на езика. Винаги помни! Всеки път, когато се използва отражение, сигурността на приложението е компрометирана.


Следващ урок за API за теми на размисъл

метод newInstance().
Разбиране на инструмента javap
създаване на javap инструмент
създаване на инструмент за преглед на аплети
Извикване на частен метод от друг клас