国产片侵犯亲女视频播放_亚洲精品二区_在线免费国产视频_欧美精品一区二区三区在线_少妇久久久_在线观看av不卡

服務器之家:專注于服務器技術及軟件下載分享
分類導航

PHP教程|ASP.NET教程|JAVA教程|ASP教程|

服務器之家 - 編程語言 - JAVA教程 - java 反射和動態代理詳解及實例代碼

java 反射和動態代理詳解及實例代碼

2020-06-19 11:32夏中偉 JAVA教程

這篇文章主要介紹了java 反射和動態代理詳解及實例代碼的相關資料,需要的朋友可以參考下

一、java中的反射

1.通過反射加載類的屬性和方法實例代碼:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
/**
     * java.lang.Class 是反射的源頭
     * 我們創建了一個類,通過編譯(javac.exe)生成對應的class文件,之后我們通過java.exe加載(jvm的類加載器加載)此class文件
     * 此class文件加載到內存后,就是一個運行時類,存在緩存區,這個運行時類本事就是一個Class的實例
     * 每一個運行時類只加載一次,
     */
    Class<StudentExam> clazz = StudentExam.class;
    StudentExam studentExam = clazz.newInstance();
    System.err.println(studentExam);
     
    System.out.println(clazz);
    // Field field = clazz.getField("id"); // 通過屬性調用運行時類的指定屬性:屬性是public類型
    Field field = clazz.getDeclaredField("id"); // 屬性是非public 類型
    Field[] fields = clazz.getDeclaredFields(); // 獲取運行時類本身(父類不行)所有聲明的屬性,父類使用clazz.getFields();
    for (Field field2 : fields) {
      int i = field2.getModifiers();
      String type = Modifier.toString(i);// 獲取字段屬性的數據類型
      System.out.println(type);
    }
    field.setAccessible(true);
    field.set(studentExam, 11);
    System.err.println(studentExam.getId());
     
    // 通過反射調用運行時類的指定方法
    Method method = clazz.getMethod("setId", Integer.class);
    method.invoke(studentExam, 123); // 調用運行時類的指定方法
    Method[] methods = clazz.getMethods(); // 獲取所有運行時類及其父類中所有聲明為public的方法
    Method[] methods2 = clazz.getDeclaredMethods();// 獲取運行時類本身類中聲明的方法
    for (Method method2 : methods) {
      System.out.println(method2.getName());
    }
     
    // * 通過對象的getClass()方法獲取對象的運行時類,
    Exam exam = new Exam();
    Class clazzExam = exam.getClass();

2.類加載器ClassLoader

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
/**
   * Description:類加載器,加載xx.properties文件,并讀取數據
   * @param
   * @author xiazhongwei
   * @data 2016年9月29日:下午5:32:56
   * @return
   */
  public void classLoader() throws IOException {
    //方法一、從當前工程下加載
    ClassLoader loader = this.getClass().getClassLoader();
    // 路徑是包下寫:com\\able\\onlineExam\\resources\\config.properties
    InputStream inStream = loader.getResourceAsStream("config.properties");
    // 方法二、從指定的路徑下加載文件
    // FileInputStream fileInputStream = new FileInputStream(new File("config.properties"));
     
    Properties properties = new Properties();
    properties.load(inStream);
    // properties.load(fileInputStream);
    String prop = properties.getProperty("domain");
    System.out.println(prop);
  }

3.動態代理

靜態代理:代理類和目標對象的類型都是在編譯期間確定下來,不利于程序的擴展。同時每個代理類只能為一個接口服務,這樣一來程序開發中必然產生過多的代理。

動態代理:客戶通過代理類來調用其他對象的方法,并且是在程序運行時,根據需要動態創建目標類的代理對象。

代理設計模式的原理:

使用一個代理將對象包裝起來,然后用該代理對象取代原始對象,任何對原始對象的調用都要通過代理,代理對象決定的那個是否以及何時將方法調用

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
package com.test.junit;
 
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
 
public class ProxyTest {
 
  public static void main(String[] args) {
    RealSubject realSubject = new RealSubject();
    MyInvocationHandler myInvocationHandler = new MyInvocationHandler();
    Object object = myInvocationHandler.bind(realSubject);
    Subject subject = (Subject) object;
    subject.action();
  }
}
// 動態代理的使用
interface Subject{
  void action();
}
// 被代理類
class RealSubject implements Subject{
 
  @Override
  public void action() {
 
    System.out.println("我是被代理類,記得執行我哦。。。。");
  }
   
}
 
class MyInvocationHandler implements InvocationHandler{
 
  Object object;// 實現了接口的被代理類的對象的聲明
  /**
   * Description:①給被代理的對象實例化 ②返回一個代理類對象
   * @param
   * @author xiazhongwei
   * @data 2016年9月29日:下午4:13:43
   * @return
   */
  public Object bind(Object object){
    this.object = object;
    return Proxy.newProxyInstance(object.getClass().getClassLoader(), object.getClass().getInterfaces(), this);
  }
  /**
   * 當通過代理類的對象發起對被重寫的方法的調用時,都會轉化為對如下的invok方法的調用
   */
  @Override
  public Object invoke(Object proxy, Method method, Object[] args)
      throws Throwable {
    Object returnObject = method.invoke(object, args);
    return returnObject;
  }
}

4.動態代理與AOP

 示例一、

?
1
2
3
4
5
6
7
8
9
package com.atguigu.spring.aop;
 
public interface ArithmeticCalculator {
  int add(int i, int j);
  int sub(int i, int j);
   
  int mul(int i, int j);
  int div(int i, int j);
}
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
 package com.atguigu.spring.aop;
 
import org.springframework.stereotype.Component;
 
@Component("arithmeticCalculator")
public class ArithmeticCalculatorImpl implements ArithmeticCalculator {
 
  @Override
  public int add(int i, int j) {
    int result = i + j;
    return result;
  }
 
  @Override
  public int sub(int i, int j) {
    int result = i - j;
    return result;
  }
 
  @Override
  public int mul(int i, int j) {
    int result = i * j;
    return result;
  }
 
  @Override
  public int div(int i, int j) {
    int result = i / j;
    return result;
  }
 
}
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
 package com.atguigu.spring.aop;
 
public class ArithmeticCalculatorLoggingImpl implements ArithmeticCalculator {
 
  @Override
  public int add(int i, int j) {
    System.out.println("The method add begins with [" + i + "," + j + "]");
    int result = i + j;
    System.out.println("The method add ends with " + result);
    return result;
  }
 
  @Override
  public int sub(int i, int j) {
    System.out.println("The method sub begins with [" + i + "," + j + "]");
    int result = i - j;
    System.out.println("The method sub ends with " + result);
    return result;
  }
 
  @Override
  public int mul(int i, int j) {
    System.out.println("The method mul begins with [" + i + "," + j + "]");
    int result = i * j;
    System.out.println("The method mul ends with " + result);
    return result;
  }
 
  @Override
  public int div(int i, int j) {
    System.out.println("The method div begins with [" + i + "," + j + "]");
    int result = i / j;
    System.out.println("The method div ends with " + result);
    return result;
  }
 
}
  
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
package com.atguigu.spring.aop;
 
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.util.Arrays;
 
public class ArithmeticCalculatorLoggingProxy {
   
  //要代理的對象
  private ArithmeticCalculator target;
   
  public ArithmeticCalculatorLoggingProxy(ArithmeticCalculator target) {
    super();
    this.target = target;
  }
 
  //返回代理對象
  public ArithmeticCalculator getLoggingProxy(){
    ArithmeticCalculator proxy = null;
    // 代理對象有哪一個類加載器負責加載
    ClassLoader loader = target.getClass().getClassLoader();
    // 代理對象的類型,即其中有哪些方法
    Class [] interfaces = new Class[]{ArithmeticCalculator.class};
    // 當調用代理對象的其中方法時,執行下面的代碼
    InvocationHandler h = new InvocationHandler() {
      /**
       * proxy: 代理對象。 一般不使用該對象
       * method: 正在被調用的方法
       * args: 調用方法傳入的參數
       */
      @Override
      public Object invoke(Object proxy, Method method, Object[] args)
          throws Throwable {
        // 在方法內部不會直接調用proxy對象的某個方法,proxy.toString()會造成死循環調用invoke方法
        String methodName = method.getName();
        //打印日志
        System.out.println("[before] The method " + methodName + " begins with " + Arrays.asList(args));
         
        //調用目標方法
        Object result = null;
         
        try {
          //前置通知
          result = method.invoke(target, args);
          //返回通知, 可以訪問到方法的返回值
        } catch (NullPointerException e) {
          e.printStackTrace();
          //異常通知, 可以訪問到方法出現的異常
        }
         
        //后置通知. 因為方法可以能會出異常, 所以訪問不到方法的返回值
         
        //打印日志
        System.out.println("[after] The method ends with " + result);
         
        return result;
      }
    };
     
    /**
     * loader: 代理對象使用的類加載器。
     * interfaces: 指定代理對象的類型. 即代理代理對象中可以有哪些方法.
     * h: 當具體調用代理對象的方法時, 應該如何進行響應, 實際上就是調用 InvocationHandler 的 invoke 方法
     */
    proxy = (ArithmeticCalculator) Proxy.newProxyInstance(loader, interfaces, h);
     
    return proxy;
  }
}
  
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
package com.atguigu.spring.aop;
 
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
 
public class Main {
   
  public static void main(String[] args) {
    // ArithmeticCalculator arithmeticCalculator = new ArithmeticCalculatorImpl();
    ArithmeticCalculator arithmeticCalculator = new ArithmeticCalculatorLoggingImpl();
     
    arithmeticCalculator = new ArithmeticCalculatorLoggingProxy(arithmeticCalculator).getLoggingProxy();
     
    int result = arithmeticCalculator.add(11, 12);
    System.out.println("result:" + result);
     
    result = arithmeticCalculator.div(21, 3);
    System.out.println("result:" + result);
     
  }
   
}

  示例二、

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
package com.test.junit;
 
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
 
public class ProxyTest {
 
  public static void main(String[] args) {
    RealSubject realSubject = new RealSubject();
    MyInvocationHandler myInvocationHandler = new MyInvocationHandler();
    Object object = myInvocationHandler.bind(realSubject);
    Subject subject = (Subject) object;
    subject.action();
  }
}
// 動態代理的使用
interface Subject{
  void action();
}
// 被代理類
class RealSubject implements Subject{
 
  @Override
  public void action() {
 
    System.out.println("我是被代理類,記得執行我哦。。。。");
  }
   
}
 
class MyInvocationHandler implements InvocationHandler{
 
  Object object;// 實現了接口的被代理類的對象的聲明
  /**
   * Description:①給被代理的對象實例化 ②返回一個代理類對象
   * @param
   * @author xiazhongwei
   * @data 2016年9月29日:下午4:13:43
   * @return
   */
  public Object bind(Object object){
    this.object = object;
    return Proxy.newProxyInstance(object.getClass().getClassLoader(), object.getClass().getInterfaces(), this);
  }
  /**
   * 當通過代理類的對象發起對被重寫的方法的調用時,都會轉化為對如下的invok方法的調用
   */
  @Override
  public Object invoke(Object proxy, Method method, Object[] args)
      throws Throwable {
    Object returnObject = method.invoke(object, args);
    return returnObject;
  }
}

感謝閱讀此文,希望能幫助到大家,謝謝大家對本站的支持!

延伸 · 閱讀

精彩推薦
主站蜘蛛池模板: 国产精品美女久久久久久久久久久 | 国产精品久久国产精品 | 成人免费视频网 | 国产精品一二三在线观看 | 亚洲综合区 | 在线免费观看毛片 | 91九色视频pron | 成人av专区| 亚洲一区电影 | 精品日韩视频 | 色日韩 | 奇米在线视频 | 爱免费视频 | 国产综合网站 | 国产精品视频久久久 | 国产成人精品一区二区三区视频 | 欧美综合在线观看 | 国产精品久久久久久久久晋中 | 国产精品乱码一区二区三区 | www.国产.com| 亚洲精品乱码久久久久久金桔影视 | 欧美激情久久久久久 | 国产亚洲精品久久久闺蜜 | 久久久国产精品 | 91中文在线观看 | 天天色天天色 | 国产偷亚洲偷欧美偷精品 | 国产精品久久久久久中文字 | 一级一片在线播放在线观看 | 亚洲国内精品 | 91麻豆蜜桃一区二区三区 | 国产午夜小视频 | 黄色av日韩 | 久久综合久色欧美综合狠狠 | 欧美日韩高清在线一区 | 免费看的av | 亚洲成人看片 | 蜜桃臀一区二区三区 | 国产剧情一区二区 | 久久国产精品一区二区三区 | 黄色av网站在线观看 |