mercyblitz 寫道
ouchxp 寫道
再就是在執行反射之前執行field.setaccessible(true); 也可以提高jdk反射效率
這樣可以提高效率?這個方法僅僅設定通路辨別,讓不能通路的成員可以通路。
keating 寫道
正如樓上mercyblitz所說,如private變量...
在此澄清一下對于setaccessable的誤解
先看一個例子
java代碼
import java.lang.reflect.invocationtargetexception;
import java.lang.reflect.method;
public class main {
public static void main(string[] args) throws securityexception, nosuchmethodexception, illegalargumentexception, illegalaccessexception, invocationtargetexception {
method m = a.class.getdeclaredmethod("getname", new class[]{});
system.out.println(m.isaccessible());
//getname是public的,猜猜輸出是true還是false
a a = new a();
a.setname("mr lee");
long start = system.currenttimemillis();
for(int i=0;i<10000000;i++){
m.invoke(a, new object[]{});
}
system.out.println( "simple :" +(system.currenttimemillis() - start));
m.setaccessible(true);//注意此處不同
long start1 = system.currenttimemillis();
system.out.println("setaccessible(true) :"+( system.currenttimemillis() - start1));
}
}
class a{
private string name;
public string getname() {
return name;
public void setname(string name) {
this.name = name;
測試結果
引用
false
simple :4969
setaccessible(true) :250
明顯 accessible并不是辨別方法能否通路的. public的方法 accessible仍為false
使用了method.setaccessible(true)後 性能有了20倍的提升
accessable屬性是繼承自accessibleobject 類. 功能是啟用或禁用安全檢查
jdk api中的解釋
accessibleobject 類是 field、method 和 constructor 對象的基類。它提供了将反射的對象标記為在使用時取消預設 java 語言通路控制檢查的能力。對于公共成員、預設(打包)通路成員、受保護成員和私有成員,在分别使用 field、method 或 constructor 對象來設定或獲得字段、調用方法,或者建立和初始化類的新執行個體的時候,會執行通路檢查。
在反射對象中設定 accessible 标志允許具有足夠特權的複雜應用程式(比如 java object serialization 或其他持久性機制)以某種通常禁止使用的方式來操作對象。
setaccessible
public void setaccessible(boolean flag)
throws securityexception
将此對象的 accessible 标志設定為訓示的布爾值。值為 true 則訓示反射的對象在使用時應該取消 java 語言通路檢查。值為 false 則訓示反射的對象應該實施 java 語言通路檢查。
實際上setaccessible是啟用和禁用通路安全檢查的開關,并不是為true就能通路為false就不能通路
由于jdk的安全檢查耗時較多.是以通過setaccessible(true)的方式關閉安全檢查就可以達到提升反射速度的目的