Помогите уяснить.
К примеру, одно из частных определений рефлексии говорит: "Рефлексия - это инструмент с помощью которого можно узнать всю информацию о классе: имена методов, параметры, поля, аннотации....".
У меня, как у новичка, возникает резонный вопрос, зачем мне эту информацию узнавать, если классы, методы, поля и т.д. я пишу сам и всё про них знаю?
Понимаю, что используется рефлексия не для своих классов и т.д., но не могу найти реальный пример, который был бы понятен новичку: в какой ситуации я столкнусь с тем, что не буду знать имя класса, метода и т.д.?
То же самое с аннотациями: "...средство, позволяющее встраивать справочную информацию в исходные файлы......". Ну встрою я её, ну а профит какой, что я в итоге с помощью этого получу? Какие плюшки для разработчика появятся при наличии аннотаций? Как они способны облегчить жизнь?
Ответ
Рефлексия и аннотации позволяют решать задачи, который в иных случаях можно было бы решить либо ручным монотонным кодированием, либо кодогенерацией.
И, конечно, когда они используются, то применяются не к конкретным классам, а с запасом, даже к тем классам, которые вы напишете в будущем. Часто их используют в библиотечном коде, который будет бродить между проектами и, соответственно, о классах тех проектов вообще не знать ничего.
Несколько конкретных примеров:
Аннотации Hibernate
Hibernate — это ORM, то есть библиотека для удобного отображения баз данных на объектный код. Часто в базе и в Java-коде применяются разные соглашения об именовании. Для того, чтобы Hibernate понимал, какое поле куда копировать, применяют аннотации. Для таблицы:
create table EMPLOYEE (
id INT NOT NULL auto_increment,
first_name VARCHAR(20) default NULL,
last_name VARCHAR(20) default NULL,
salary INT default NULL,
PRIMARY KEY (id)
);
Можно применить аннотации:
@Entity
@Table(name = "EMPLOYEE")
public class Employee {
@Id @GeneratedValue
@Column(name = "id")
private int id;
@Column(name = "first_name")
private String firstName;
@Column(name = "last_name")
private String lastName;
@Column(name = "salary")
private int salary;
public Employee() {}
public int getId() {
return id;
}
public void setId( int id ) {
this.id = id;
}
public String getFirstName() {
return firstName;
}
public void setFirstName( String first_name ) {
this.firstName = first_name;
}
public String getLastName() {
return lastName;
}
public void setLastName( String last_name ) {
this.lastName = last_name;
}
public int getSalary() {
return salary;
}
public void setSalary( int salary ) {
this.salary = salary;
}
}
Пример взят отсюда. Кратко, что здесь происходит: в базе данных поле называется, например, first_name, а в Java-коде — firstName. Благодаря аннотациям при загрузке записей из базы в объект Employee библиотека самостоятельно раскидает все поля как надо.
Компилятор Java
Компилятор также использует аннотации для дополнительных проверок или для изменения своих настроек внутри отдельных методов. Смотрите аннотации @Override и @SuppressWarnings
AndroidAnnotations
Проект http://androidannotations.org/ позволяет значительно упростить разработку кода для Android, реализовав частые задачи, и обернув их в аннотации. Это как раз хороший пример библиотечного кода, который будет работать в незнакомых проектах. Естественно, для реализации этого кода активно применяется рефлексия. Пример «до аннотаций» и «после аннотаций» приведён прямо на главной странице по ссылке выше.
Аспектно-ориентированное программирование
Про него много писать не буду, поскольку тема очень большая и новичку может быть не сильно нужная. Но в целом АОП как раз об этом. Например, вы можете написать свои классы, а потом озаботится проверкой прав доступа, навроде администратор может удалять записи, а обычный пользователь — нет
При классическом подходе вам придётся вносить однотипные изменения в большое количество существующих классов, а потом не забывать делать это для новых. В АОП вы можете просто придумать аннотации @Administrator, @User, @Moderator и расставить их у нужных классов и методов. Это тоже монотонно, но всё равно гораздо проще.
Рефлексия без аннотаций
Рефлексия применяется ещё чаще, например, в разного рода шаблонизаторах и мапперах. Шаблонизаторы позволяют вам использовать шаблоны писем, например, как этот:
Здравствуйте, %username%!
Напоминаем Вам, что вы задолжали нам крупную сумму денег в размере %amount%
рублей. Мы помним!
С уважением,
Коллекторское агентство «Солнышко»
Затем вы передаете шаблонизатору класс с полями username и amount и он самостоятельно сформирует текст письма. Такую задачу без рефлексии не сделать.
Заключение
В целом, рефлексия и аннотации позволяют избавиться от так называемого monkey coding, то есть от монотонного низкоуровнего кодирования.
Комментариев нет:
Отправить комментарий