Java 的反射 java.lang.reflect
准备一个班级。
class Person {
private String name = "tony";
private int age = 41;
public Person() {
}
public Person(String name , int age ) {
this.name = name;
this.age = age;
}
@Override
public String toString() {
// TODO 自動生成されたメソッド・スタブ
return String.format("名前は%s,年齢は%d", name,age);
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}
获取2个类的方法
private static void demoClassName() {
Class<?> class1 = Date.class;
System.out.println("--Date.class--");
System.out.println(class1.getName());
System.out.println(class1.getSimpleName());
java.util.Date date = new java.util.Date();
Class<?> class2 = date.getClass();
System.out.println("--date.getClass()--");
System.out.println(class2.getName());
System.out.println(class2.getSimpleName());
Class<?> class3;
try {
class3 = Class.forName("com.yanheng.reflect.Person");
System.out.println(class3.getName());
System.out.println(class3.getSimpleName());
} catch (ReflectiveOperationException e) {
e.printStackTrace();
}
}
生成3个实例的方法(无参数)
private static void demoCreateInstance() {
Class<?> class3;
try {
class3 = Class.forName("com.yanheng.reflect.Person");
Person person = (Person) class3.newInstance();
System.out.println(person.toString());
} catch (ReflectiveOperationException e) {
e.printStackTrace();
}
}
生成4个实例的方法(带参数)
private static void demoConstructor() {
try {
Class<?> clazz = Class.forName("com.yanheng.reflect.Person");
Constructor constructor = clazz.getConstructor(String.class , int.class);
Person person = (Person) constructor.newInstance("阿部",25);
System.out.println(person.toString());
} catch (ClassNotFoundException e) {
e.printStackTrace();
} catch (InstantiationException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (IllegalArgumentException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
} catch (NoSuchMethodException e) {
e.printStackTrace();
} catch (SecurityException e) {
e.printStackTrace();
}
}
如何调用1.5个实例的方法
private static void demoMethod() {
Person person;
Class<?> clazz;
Method methodsetName;
Method methodSetAge;
try {
clazz = Class.forName("com.yanheng.reflect.Person");
person = (Person) clazz.newInstance();
methodsetName = clazz.getMethod("setName", String.class);
methodSetAge = clazz.getMethod("setAge", int.class);
methodsetName.invoke(person, "Tom");
methodSetAge.invoke(person, 32);
System.out.println(person.toString());
} catch (InstantiationException | IllegalAccessException | ClassNotFoundException e) {
// TODO 自動生成された catch ブロック
e.printStackTrace();
} catch (NoSuchMethodException e) {
// TODO 自動生成された catch ブロック
e.printStackTrace();
} catch (SecurityException e) {
// TODO 自動生成された catch ブロック
e.printStackTrace();
} catch (IllegalArgumentException e) {
// TODO 自動生成された catch ブロック
e.printStackTrace();
} catch (InvocationTargetException e) {
// TODO 自動生成された catch ブロック
e.printStackTrace();
}
}
调用1.5个私有实例字段的方法
private static void demoLocalVariable() {
Person person;
Class<?> clazz;
Field fieldName;
Field fieldAge;
try {
clazz = Class.forName("com.yanheng.reflect.Person");
person = (Person) clazz.newInstance();
fieldName = clazz.getDeclaredField("name");
fieldName.setAccessible(true);
fieldName.set(person, "Jack");
fieldAge = clazz.getDeclaredField("age");
fieldAge.setAccessible(true);
fieldAge.set(person, 23);
System.out.println(person.toString());
} catch (ClassNotFoundException e) {
// TODO 自動生成された catch ブロック
e.printStackTrace();
} catch (InstantiationException e) {
// TODO 自動生成された catch ブロック
e.printStackTrace();
} catch (IllegalAccessException e) {
// TODO 自動生成された catch ブロック
e.printStackTrace();
} catch (NoSuchFieldException e) {
// TODO 自動生成された catch ブロック
e.printStackTrace();
} catch (SecurityException e) {
// TODO 自動生成された catch ブロック
e.printStackTrace();
}
}
应用设计工厂
准备2.1接口和类。
interface Fruit {
void eat();
}
class Apple implements Fruit {
@Override
public void eat() {
System.out.println("リンゴおいしい");
}
}
class Lemon implements Fruit {
@Override
public void eat() {
System.out.println("レモン酸っぱいよ");
}
}
为2.2工厂做准备
class FruitFactory {
public static Fruit getInstance(String fruitName) {
Fruit fruit = null;
try {
fruit = (Fruit) Class.forName(fruitName).newInstance();
} catch (ClassNotFoundException e) {
// TODO 自動生成された catch ブロック
e.printStackTrace();
} catch (InstantiationException | IllegalAccessException e) {
// TODO 自動生成された catch ブロック
e.printStackTrace();
}
return fruit;
}
}
2.3工厂演示
private static void demoFactory() {
String name = "com.yanheng.reflect.Apple";
Fruit fruit = FruitFactory.getInstance(name);
fruit.eat();
name = "com.yanheng.reflect.Lemon";
Fruit fruit2 = FruitFactory.getInstance(name);
fruit2.eat();
}
3个示例代码
4new和reflect的比较
用new关键字创建实例:
优点:速度快
通过反射创建实例:
优点:具有良好的扩展性。
对Android框架的应用
在启动时使用”startActivity(intent)”来创建activity的实例并调用onCreate。
Flamework如何创建实例?
让我们来查看一下代码吧,在ActivityThread中。
private Activity performLaunchActivity(ActivityClientRecord r, Intent customIntent) {
ContextImpl appContext = createBaseContextForActivity(r);
Activity activity = null;
try {
java.lang.ClassLoader cl = appContext.getClassLoader();
activity = mInstrumentation.newActivity(
cl, component.getClassName(), r.intent);
StrictMode.incrementExpectedActivityCount(activity.getClass());
r.intent.setExtrasClassLoader(cl);
r.intent.prepareToEnterProcess();
if (r.state != null) {
r.state.setClassLoader(cl);
}
} catch (Exception e) {
使用される中国語のネイティブ表現を求めています。ただし、1つのオプションだけで結構です。
在AppComponentFactory中使用。
public @NonNull Activity instantiateActivity(@NonNull ClassLoader cl, @NonNull String className,
@Nullable Intent intent)
throws InstantiationException, IllegalAccessException, ClassNotFoundException {
return (Activity) cl.loadClass(className).newInstance();
}
在这里,通过类名生成了一个实例。