標籤:指標 integercache java引用 整型比較
JAVA中沒有指標一說,但也有引用的概念。這裡要說的主要是Integer是不是同一個對象。
1、先看一段代碼:
public static void main(String[] args){Integer a1 = 100;Integer b1 = a1;//另一種也可以b1=100Field field = null;try {field = a1.getClass().getDeclaredField("value");} catch (NoSuchFieldException e) {// TODO Auto-generated catch blocke.printStackTrace();} catch (SecurityException e) {// TODO Auto-generated catch blocke.printStackTrace();} field.setAccessible(true); try {field.set(a1, 5000);} catch (IllegalArgumentException e) {// TODO Auto-generated catch blocke.printStackTrace();} catch (IllegalAccessException e) {// TODO Auto-generated catch blocke.printStackTrace();} System.out.println("b1="+b1); Integer c1 = 100; System.out.println("c1="+c1); }
結果:
b1=5000
c1=5000
從上面,首先這裡要說明幾個,
1)、對於Integer來說,-128-127之間的整型已經初始化放在IntegerCache中,如果是裝箱的話,就會從這裡面取對象。
2)、b1=a1到底是數字賦值還是同一個對象?這個從結果實際就可以看出來,b1和a1指向同一個對象,而不是同一個數值
3)、c1=100,說明對於-128-127之間的數值,都是從IntegerCache中擷取的對象,100對應的Integer對象被改變後,後續對於100的裝箱都被改變。因為擷取cache中對象時用的是數組索引,而不是數值比較擷取的。
不過修改這個緩衝會比較危險,不介意。誰知道什麼jar包或者什麼平台來個100的裝箱,但得到結果又不是100,到時就崩潰了。
2、通過上面描述,那麼如果改成這樣又是什麼答案
public static void main(String[] args){Integer a1 = 200;Integer b1 = a1;Field field = null;try {field = a1.getClass().getDeclaredField("value");} catch (NoSuchFieldException e) {// TODO Auto-generated catch blocke.printStackTrace();} catch (SecurityException e) {// TODO Auto-generated catch blocke.printStackTrace();} field.setAccessible(true); try {field.set(a1, 5000);} catch (IllegalArgumentException e) {// TODO Auto-generated catch blocke.printStackTrace();} catch (IllegalAccessException e) {// TODO Auto-generated catch blocke.printStackTrace();} System.out.println("b1="+b1); Integer c1 = 200; System.out.println("c1="+c1); }
3、那麼再改一下
public static void main(String[] args){Integer a1 = new Integer(100);Integer b1 = a1;Field field = null;try {field = a1.getClass().getDeclaredField("value");} catch (NoSuchFieldException e) {// TODO Auto-generated catch blocke.printStackTrace();} catch (SecurityException e) {// TODO Auto-generated catch blocke.printStackTrace();} field.setAccessible(true); try {field.set(a1, 5000);} catch (IllegalArgumentException e) {// TODO Auto-generated catch blocke.printStackTrace();} catch (IllegalAccessException e) {// TODO Auto-generated catch blocke.printStackTrace();} System.out.println("b1="+b1); Integer c1 = 100; System.out.println("c1="+c1); }這又是什麼答案。對於new的操作,是不進行裝箱的,而是在堆中產生對象的。
理解了裝箱、緩衝、引用就不難理解了。可以自己試試。
JAVA中Integer對象的引用