通过注解给一个方法或者属性注入一个对象。
利用反射技术,可以将注解信息注入到一个对象中。如下:使用注解向一个方法注入一个Person对象。
public class PersonDao {
private Person person;
PersonDao(Person person){
this.person = person;
}
public PersonDao() {
// TODO Auto-generated constructor stub
}
public Person getPerson() {
return person;
}
@InjectPerson(name="zhangsan", age=21)//通过注解,可以想此方法注入一个person对象
public void setPerson(Person person) {
this.person = person;
}
}
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
@Retention(RetentionPolicy.RUNTIME)
public @interface InjectPerson {
String name() default "lisi";
int age() default 23;
}
public class Person {
private String name;
private int age;
/**
* @return the name
*/
public String getName() {
return name;
}
/**
* @param name the name to set
*/
public void setName(String name) {
this.name = name;
}
/**
* @return the age
*/
public int getAge() {
return age;
}
/**
* @param age the age to set
*/
public void setAge(int age) {
this.age = age;
}
}
反射框架代码示例:获取注解相关信息,并将其注入到一个Person对象中,再将此person对象注入到其对应的方法中。
//1.获取要注入的属性
PropertyDescriptor pd = new PropertyDescriptor("person", PersonDao.class);
//2.获取注入属性的类型
Class<?> clazz = pd.getPropertyType();
//3.创建一个属性实例对象
Object person = clazz.newInstance();
//4.获取这个要注入属性的写方法
Method setPerson = pd.getWriteMethod();
//5.获取此写方法上的注解
InjectPerson inject = setPerson.getAnnotation(InjectPerson.class);
//6.获取此注解上所有属性值,并将其注入到person对象中
Method methods[] = inject.getClass().getMethods();
for(Method m : methods){
if(m!=null){
//7.获取属性对应的名称
String methodName = m.getName();
try{
//8.获取要注入类型的与此方法对应的变量
Field f = Person.class.getDeclaredField(methodName);
System.out.println(f);
if (f!=null){
//获取此属性的值
Object value = m.invoke(inject);
f.setAccessible(true);
//将此值注入到person对象中, 调用
f.set(person, value);
}
}catch(Exception e){
continue;
}
}
}
//9.将person对象注入到PersonDao中
PersonDao dao = new PersonDao();
dao.setPerson((Person)person);
System.out.println(dao.getPerson().getName());
System.out.println(dao.getPerson().getAge());
//打印输出:
lisi
32
想一个属性上注入一个对象示例:
public class PersonDao {
@InjectPerson(name="张三", age=40) private Person person; //根据此属性上的注解,注入一个person
public PersonDao() {
}
public PersonDao(Person person){
super();
this.person = person;
}
public Person getPerson() {
return person;
}
@InjectPerson(name="lisi", age=32)
public void setPerson(Person person) {
this.person = person;
}
}
//1.获取要注入的属性
Field fPerson = PersonDao.class.getDeclaredField("person");
//2.获取要注入的属性类型
Class clazz = fPerson.getType();
//3.创建一个此类型的实体对象
Object person = clazz.newInstance();
//4.获取此域上的注解信息
InjectPerson inject = fPerson.getAnnotation(InjectPerson.class);
//5.获取此注解上的所有信息,并填充到person对象中
Method[] methods = inject.getClass().getMethods();
for(Method m : methods){
if(m!=null){
String methodName = m.getName();
try{
//方法一:利用反射方法将注解值注入到person对应的属性上
// Field f = person.getClass().getDeclaredField(methodName);
// if(f!=null){
// Object value = m.invoke(inject);
// f.setAccessible(true);
// f.set(person, value);
// }
//利用PropertyDescriptor来实现
PropertyDescriptor pd = new PropertyDescriptor(methodName, Person.class);
Method setPerson = pd.getWriteMethod(); //获取setName setAge
setPerson.invoke(person, m.invoke(inject));
}catch(Exception e){
continue;
}
}
}
//将person注入
// PersonDao dao = new PersonDao((Person)person);
PersonDao dao = new PersonDao();
fPerson.setAccessible(true);
fPerson.set(dao, person);
System.out.println(dao.getPerson().getAge());
System.out.println(dao.getPerson().getName());
}
输出:
40
张三
值得注意的是:可以使用PropertyDescriptor和反射技术来实现根据注解信息。