isXXX()的方法是很經常見的一類方法,其中,在反射類庫中的Class 類就有isArray()這一方法,由下文的代碼運行可以得到一個結論:就是ArrayList對象不能通過isArray()的檢驗,其實很大程度是我先入為主的認為ArrayList是Array,為什么會這樣認為呢?一方面是因為類名上有Array的字樣,另一方面就是認為ArrayList可能是實現了一個叫Array的接口。查api可以知道,其實并沒有這樣一個接口,只有反射庫里有這么一個類,當然和ArrayList沒什么關系啦。明白了這點,就可以知道其實isArray()方法的判斷就不是接口了。
結合下面代碼的結果可以知道,其實isArray()是以“[]”來判斷的,至于怎么實現,小弟能力有限。
事實上,ArrayList對象中有elementData這一Object[]變量,所以,在代碼的第一次遞歸前,利用反身機制獲得了這一Field并進入toString遞歸,并通過了isArray()的檢驗。
另外:由打印出來的消息可以知道,如果將兩個return分成兩部分,則,前面的只調用過1次,后面的調用了5次,那是因為數組Object[] elementData在接收了原型數據int后會將int自動封裝成java.lang.Integer對象,所以getComponent()獲得的是Integer類型,而非原型int,因此遞歸調用toString()。
第一次寫BLOG,哈哈,馬馬虎虎,請見諒
以下是一段Core Java里的一個例子,加上我自己的調試語句:
import java.lang.reflect.AccessibleObject;
import java.lang.reflect.Array;
import java.lang.reflect.Field;
import java.lang.reflect.Modifier;
import java.util.ArrayList;
import java.util.Date;
import java.util.LinkedList;
public class ObjectAnalyzerTest {
public static void main(String [] args){
ArrayList<Integer> squares=new ArrayList<Integer>();
for(int i=1; i<=5;i++)squares.add(i*i);
System.out.println(new ObjectAnalyzer().toString(squares));
}
}
class ObjectAnalyzer{
public String toString(Object obj){
if(obj==null)return "null";
if(visited.contains(obj))return "...";//************
visited.add(obj);
Class cl=obj.getClass();
if(cl==String.class)return (String)obj;
if(cl.isArray()){
// System.out.println(cl.getName()+"+"+"1+"+re++);
String r = cl.getComponentType()+"[]{";
for (int i = 0;i < Array.getLength(obj);i++){
if (i>0)r+=",";
Object val = Array.get(obj,i);
if (cl.getComponentType().isPrimitive()) r+=val;
else r += toString(val);
}
System.out.println("X+"+r);
return r+"}";
}
String r = cl.getName();
// System.out.println(cl.getName()+"+"+"0+"+re++);
do
{
r+="[";
Field[] fields=cl.getDeclaredFields();
AccessibleObject.setAccessible(fields,true);
for(Field f:fields){
if(!Modifier.isStatic(f.getModifiers())){
if(!r.endsWith("["))r+=",";
r+= f.getName()+"=";
try{
Class t = f.getType();
Object val = f.get(obj);
if(t.isPrimitive()) r+=val;
else r+=toString(val);
}catch(Exception e){
e.printStackTrace();
}
}
}
r+="]";
cl=cl.getSuperclass();
}
while(cl!=null);
System.out.println("X+"+r);
return r;
}
private ArrayList<Object> visited=new ArrayList<Object>();
private int re=0;
}