本文主要是介绍Java学习--day05,对大家解决编程问题具有一定的参考价值,需要的程序猿们随着小编来一起学习吧!
反射
- 反射机制:通过一个抽象的类名能在自己记忆(加载类的内存)中找到匹配的类的具体信息。
//理解class类并实例化Class类对象
Person p = new Person();
//实例化Class类对象的四种方法
Class c = Person.class;//通过类的class属性获取,最为安全可靠,程序性能最高
Class c1 = p.getClass();//通过某个类的实例获取
try {
Class c2 = Class.forName("day13.Person");//通过Class的静态方法forname来获取一个类的class实例,常用方法
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
// ClassLoader cl = this.getClass().getClassLoader();
// try {
// Class c3 = cl.loadClass("day13.Person");
// } catch (ClassNotFoundException e) {
// e.printStackTrace();
// }
//运行时创建对象并获取类的完整结构:
//获得父类
Class superclass = c.getSuperclass();
System.out.println("父类:"+superclass.getName());
//获得接口
Class[] interfaces = c.getInterfaces();
for (Class c1 : interfaces) {
System.out.println("接口"+c1.getName());
}
//获得构造器
Class c = Class.forName("day13.Person");
Constructor[] con = c.getConstructors();//获取公有的构造器
for (Constructor con1 :con){
System.out.println("构造方法名"+con1.getName());
System.out.println("构造方法修饰符为"+con1.getModifiers());
Class[] c2 = con1.getParameterTypes();
for(Class clazz :c2){
System.out.println(clazz);
}
System.out.println("--------------");
}
Constructor[] con2 = c.getDeclaredConstructors();//获取所有构造器
for (Constructor con3 :con2){
System.out.println("构造方法名"+con3.getName());
System.out.println("构造方法修饰符为"+con3.getModifiers());
Class[] c3 = con3.getParameterTypes();
for(Class clazz1 :c3){
System.out.println(clazz1);
}
System.out.println("--------------");
}
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
//创建对象
Class clazz = Class.forName("day13.Student");
Object obj = clazz.newInstance();//相当于调用无参构造
Student s = (Student) obj;
System.out.println(s.school);
Constructor c = clazz.getConstructor(String.class);//调用一个参数的构造
Student stu = (Student)c.newInstance("张三");
System.out.println(stu.name);
Constructor c = clazz.getDeclaredConstructor(String.class,String.class);//调用两个参数的构造
c.setAccessible(true);//解除私有的封装,下面就可以对这个私有方法强制使用
Student stu = (Student) c.newInstance("李四","希望小学");
System.out.println(stu.name+stu.school);
//获得方法
Method[] ms = clazz.getDeclaredMethods();//获取类的所有方法
for(Method m : ms){
System.out.println("方法的名称"+m.getName());
System.out.println("方法的修饰符"+m.getModifiers());
System.out.println("返回值的类型"+m.getReturnType());
Class[] cl = m.getParameterTypes();
if(cl != null && cl.length > 0){
for(Class c : cl){
System.out.println("参数类型"+c.getName());
}
}
System.out.println("------------");
}
//获得属性
//Field[] f= clazz.getFields();//获得公有的
Field[] f= clazz.getDeclaredFields();//获得所有的
for (Field f1 : f) {
System.out.println("属性的名称"+f1.getName());
System.out.println("属性的修饰符"+f1.getModifiers());
System.out.println("属性的类型"+f1.getType());
System.out.println("---------");
}
//获得包名
Package p = clazz.getPackage();
System.out.println(p.getName());
//通过反射调用类的指定方法、指定属性
//指定方法
Constructor c = clazz.getConstructor(String.class);
Object obj = c.newInstance("张三");
Method m = clazz.getMethod("setInfo", String.class, String.class);
m.invoke(obj,"张三","希望小学");
Method m1 = clazz.getDeclaredMethod("test",String.class);
m1.setAccessible(true);//解除私有封装,下面可以调用
m1.invoke(obj,"张三");
//调用有返回值的方法
Method m2 = clazz.getMethod("getSchool");
String s = (String)m2.invoke(obj);
System.out.println(s);
//指定属性
Constructor con = clazz.getConstructor(String.class);
Student s = (Student) con.newInstance("沙城一小");
Field f = clazz.getField("school");
f.set(s,"希望小学");
System.out.println(f.get(s));
Field f1 = clazz.getDeclaredField("privateField");//访问私有
f1.setAccessible(true);
f1.set(s,"1");
System.out.println(f1.get(s));
//1.创建一个实现接口的InvocationHandel的类,它必须实现invoke方法,以完成代理的具体操作。
public class ProxyDemo implements InvocationHandler {
Object obj;
public ProxyDemo(Object obj){
this.obj =obj;
}
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
System.out.println(method.getName()+"方法开始执行");
Object result = method.invoke(this.obj,args);//执行的是指定的代理对象的指定的方法
System.out.println(method.getName()+"方法执行完毕");
return result;
}
}
//2.创建被代理的类以及接口
public class TestDemoImp1 implements ITestDemo{
@Override
public void test1() {
System.out.println("执行test1");
}
@Override
public void test2() {
System.out.println("执行test2");
}
@Override
public void test3() {
System.out.println("执行test3");
}
}
public interface ITestDemo {
void test1();
void test2();
void test3();
}
//3.通过Proxy的静态方法newProxyInstance(ClassLoader Loader,Class[] interfaces,InvocationHandler h)创建一个Subject接口代理。
ITestDemo t = new TestDemoImp1();
InvocationHandler handler = new ProxyDemo(t);
/**
* 第一个参数是代理对象的类加载器
* 第二个参数是代理对象的接口
* 第三个参数是代理对象
* 返回的值是成功被代理后对象,返回的是Object类型
*/
ITestDemo t1 =(ITestDemo)Proxy.newProxyInstance(handler.getClass().getClassLoader(),t.getClass().getInterfaces(),handler);
/**
* 如果一个代理类想要被 Proxy.newProxyInstance方式代理那么这个对象的类一定要有对应的接口
* 就像本例中的接口ITestDemo和实现类TestDemoImp1一样
*/
//4.通过Subject代理调用RealSubject实现类的方法。
t1.test1();
t1.test2();
t1.test3();
这篇关于Java学习--day05的文章就介绍到这儿,希望我们推荐的文章对大家有所帮助,也希望大家多多支持为之网!