麻豆小视频在线观看_中文黄色一级片_久久久成人精品_成片免费观看视频大全_午夜精品久久久久久久99热浪潮_成人一区二区三区四区

首頁 > 開發 > Java > 正文

Java高級特性之反射機制實例詳解

2024-07-14 08:42:13
字體:
來源:轉載
供稿:網友

本文實例講述了Java高級特性之反射機制。分享給大家供大家參考,具體如下:

老規矩我們還是先提出幾個問題,一門技術必然要能解決一定的問題,才有去學習掌握它的價值

  • 一、 什么是反射?
  • 二、反射能做什么?

一、 什么是反射?

用在Java身上指的是我們可以于運行時加載、探知、使用編譯期間完全未知的classes。換句話說,Java程序可以加載一個運行時才得知名稱的class,獲悉其完整構造(但不包括methods定義),并生成其對象實體、或對其fields設值、或喚起其methods

如果你是一個Android Developer,前輩們都會教導你盡量少用反射,效率太低,太慢。“射”嘛,射的太快就不好了,所以反射雖然慢點,但是偶爾射一下還是很”爽”的。

二、反射能做什么?

1、新建類的實例

我們知道所有的類都繼承子頂級父類Object,而Object中有hashCode()equals()clone()toString()getClass()等。其中getClass()返回一個Class 對象。我們這里就需要使用的Class對象,注意C是大寫,我們可以通過一下方式來獲取Class對象

  • 1.Class.forName("類名字符串") (注意:類名字符串必須是全稱,包名+類名)
  • 2.類名.class
  • 3.實例對象.getClass()

在Class類中有一個非常重要的方法

public T newInstance() throws InstantiationException, IllegalAccessException {    return newInstanceImpl();}private native T newInstanceImpl() throws IllegalAccessException, InstantiationException;

查看Api可以看到調用newInstace方法可以返回當前class對應的實例對象。接下來看一個小的Demo

public class Reflection {  public static void main(String[] args) {    // 普通創建類的實例    People p1 = new People();    System.out.println(p1.getName());    // 利用反射獲取類的實例    Class clazz = People.class;    // 常用方式,注意括號中需要放類的全路徑名    // Class clazz = Class.forName("reflection.People");    // Class clazz = p1.getClass();    try {      People p2 = (People) clazz.newInstance();      System.out.println(p2.getName());    } catch (Exception e) {      e.printStackTrace();    }  }}class People {  private String name = "張三";  private int 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、獲取成員變量和方法

在講之前我們先來看這樣一個小按理,JSON數據轉JavaBaen對象,在不用解析庫的情況下,一般我們會這樣做

private void analysisDate(JSONObject response) throws JSONException {    int announceid = response.getInt("announceid");    String    String hits = response.getString("hits");    String addtime = response.getString("addtime");    NewsNotifyItem newsNotifyItem = new NewsNotifyItem(announceid,        title, hits, addtime);  }}

每當我們需要解析額時候,都需要根據不同javabean來進行相應的解析,我們每次進行的操作都是一樣的,只是解析的數據不同而已,結合上篇帖子講到的泛型,這里我們就可以再利用反射來自己做一個Json解析工具

下面 是我寫的一個JsonObject對象轉JavaBean的一個工具類,需要注意的是,JSON的key需要和字段名保持一致,先說下思路

①首先通過反射獲取JavaBean中的所有字段值的名稱
②拼接出set方法
③由于字段名和Json的key值相同,利用自動名獲取Json中的值并填充的實例對象中

public class Json2BeanUtils {  public static <T> T jsonToBean(JSONObject response, Class<T> clazz) {    try {      // 創建類的實例      Object object = Class.forName(clazz.getName()).newInstance();      // 獲取類中的所有成員變量      Field[] fields = object.getClass().getDeclaredFields();      for (int i = 0; i < fields.length; i++) {        //設置權限        fields[i].setAccessible(true);        // 獲取字段的名稱        String fieldName = fields[i].getName();        // 過濾掉UID        if (fieldName.endsWith("serialVersionUID")) {          continue;        }        // 獲取字段的類型        String fieldType = fields[i].getGenericType().toString();        // 拼接出JavaBean中的set方法 這里有一個坑 后面講解        String methodName = "set"            + fieldName.substring(0, 1).toUpperCase()            + fieldName.substring(1);        try {          // 判斷變量類型          if (fieldType.endsWith("class java.lang.String")) {            // 獲取到set方法            Method m = object.getClass().getMethod(methodName,                String.class);            String value = null;            try {              // 從JsonObj中取出相應的值              value = response.getString(fieldName);            } catch (Exception e) {              e.printStackTrace();              value = "";            }            if (TextUtils.isEmpty(value)) {              value = "";            } else if (value.endsWith("null")) {              value = "";            }            // 賦值            m.invoke(object, value);          } else if (fieldType.endsWith("int")              || fieldType.endsWith("class java.lang.Integer")) {            // int 類型            System.out.println();            Method m = object.getClass().getMethod(methodName,                int.class);            int value = -1;            try {              value = response.getInt(fieldName);            } catch (Exception e) {              e.printStackTrace();              value = -1;            }            m.invoke(object, value);          } else if (fieldType.endsWith("boolean")              || fieldType                  .endsWith("fieldType:class java.lang.Boolean")) {            // boolean 類型            Method m = object.getClass().getMethod(methodName,                boolean.class);            boolean value = false;            try {              value = response.getBoolean(fieldName);            } catch (Exception e) {              e.printStackTrace();              value = false;            }            m.invoke(object, value);          } else if (fieldType.endsWith("double")              || fieldType                  .endsWith("fieldType:class java.lang.Double")) {            // double 類型            Method m = object.getClass().getMethod(methodName,                double.class);            double value = -1D;            try {              value = response.getDouble(fieldName);            } catch (Exception e) {              e.printStackTrace();              value = -1D;            }            m.invoke(object, value);          } else if (fieldType.endsWith("char")) {            // char類型 JSONObject 沒有char            Method m = object.getClass().getMethod(methodName,                String.class);            String value = "";            try {              value = response.getString(fieldName);            } catch (Exception e) {              e.printStackTrace();              value = "";            }            m.invoke(object, value);          } else if (fieldType.endsWith("float")              || fieldType                  .endsWith("fieldType:class java.lang.Float")) {            // float類型            Method m = object.getClass().getMethod(methodName,                double.class);            double value = -1D;            try {              value = response.getDouble(fieldName);            } catch (Exception e) {              e.printStackTrace();              value = -1D;            }            m.invoke(object, value);          } else if (fieldType.endsWith("short")              || fieldType                  .endsWith("fieldType:class java.lang.Short")) {            // short            Method m = object.getClass().getMethod(methodName,                short.class);            int value = -1;            try {              value = response.getInt(fieldName);            } catch (Exception e) {              e.printStackTrace();              value = -1;            }            m.invoke(object, value);          } else if (fieldType.endsWith("byte")              || fieldType                  .endsWith("fieldType:class java.lang.Byte")) {            Method m = object.getClass().getMethod(methodName,                byte.class);            int value = -1;            try {              value = response.getInt(fieldName);            } catch (Exception e) {              e.printStackTrace();              value = -1;            }            m.invoke(object, value);          } else if (fieldType.endsWith("long")              || fieldType                  .endsWith("fieldType:class java.lang.Long")) {            Method m = object.getClass().getMethod(methodName,                long.class);            Long value = -1L;            try {              value = response.getLong(fieldName);            } catch (Exception e) {              e.printStackTrace();              value = -1L;            }            m.invoke(object, value);          }        } catch (Exception e) {          // TODO: handle exception        }      }      return (T) object;    } catch (Exception e) {      e.printStackTrace();    }    return null;  }}

這里需要注意一個坑,先來看一段代碼

class People {  private String name;  private int age;  private String mSex;  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;  }  public String getmSex() {    return mSex;  }  // 這里就出了問題  public void setmSex(String mSex) {    this.mSex = mSex;  }}

當我們自動生成get set方法時,會將字段的首字母大寫,我們在上面拼接set 方法時,也是基于這樣的規則來拼裝的。但是 當我們的字段名為 aAbbb 時,則生成的get set 方法則不會大寫。解決方案也很簡單,注意字段命名或者在拼接時對第二個自動進行大小寫判斷。這樣我們自己寫的Json解析工具就搞定, 以后每次解析只需一行代碼即可OK。

今天反射就暫時講到這里。其實反射的作用遠不于此,這里只是使用了反射的冰山一角,結合注解和泛型,反射可以做的事更多,但是還是和開頭講的一樣,反射用起來雖然很爽,但是不能亂射,和頻繁的射,“射”的太多。“性”能會出問題!(o(∩_∩)o )。

希望本文所述對大家java程序設計有所幫助。


注:相關教程知識閱讀請移步到JAVA教程頻道。
發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 国产亚洲精品久久午夜玫瑰园 | 激情免费视频 | 成人免费影院 | www.狠狠插.com| 国产91一区| 全黄性性激高免费视频 | 欧美综合在线观看视频 | 美女黄污视频 | 毛片在线视频观看 | 主播粉嫩国产在线精品 | 视频一区国产 | 日韩视频在线观看免费视频 | 黄色毛片免费看 | 日本不卡一区二区三区在线观看 | 特级黄色小说 | 本站只有精品 | 性大片免费看 | 免费视频a | 嗯~啊~用力~高h | 国产精品一区二区三区99 | 黄视频在线网站 | 婷婷久久久久久 | 男人的天堂色偷偷 | 日韩精品久久久久久久电影99爱 | 精品中文字幕在线观看 | av噜噜在线 | 国产91片 | 成人毛片100部 | 亚洲免费毛片基地 | 操操操日日日干干干 | 成人精品免费在线观看 | 免费一级欧美大片视频 | 激情亚洲一区二区 | 欧洲成人综合网 | 中文字幕xxx| 精品国产一区二区三区久久久 | av在线视 | 久久精品视频免费观看 | 色戒在线版| 国产午夜精品视频免费不卡69堂 | 日本免费aaa观看 |