熱點推薦:
您现在的位置: 電腦知識網 >> 編程 >> Java編程 >> Java核心技術 >> 正文

如何計算java對象占用的內存

2013-11-23 19:12:42  來源: Java核心技術 

  Java有一個很好的地方就是java的垃圾收集機制這個機制集成於jvm的對程序員來說是隱藏且不透明的這種情況下如何得到某個對象消耗的內存呢?
  
    曾經看到過有人用以下方法來計算在生成該object的前後都調用javalangRuntimefreeMemory()方法然後看兩者之差即為該object消耗的內存量
  
    這種方法的代碼是
  
  long totalMem = javalangRuntimefreeMemory();
  Object myBigObject = null;
  Systemoutprintln(You just got rid of + totalMem
   javalangRuntimefreeMemory());
  
  
  
    這種想法是對的但是實際上jvm的freememory往往不能正確反應實際的free memory比如在jvm要進行垃圾收集的時候free memory就會縮小而如果決定垃圾收集的時間發生在該object生成之後而在第二次調用javalangRuntimefreeMemory()之前那麼就會錯誤地增加該object消耗的內存量
  
    在java專家By Tony Sintes的文章Discover how much memory an object consumes 裡面提到了應該用RuntimegetRuntime()totalMemory();並且計算兩次之差來得到消耗的內存量
  
    By Tony Sintes的源代碼
  
  public class Memory {
   private final static int _SIZE = ;
   public static void main( String [] args )
   throws Exception {
   Object[] array = new Object[_SIZE];
   RuntimegetRuntime()gc();
   long start = RuntimegetRuntime()totalMemory();
   for (int i = ; i < _SIZE; i++) {
   array[i] = new Object();
   }
   Runtime.getRuntime().gc();
   long end = Runtime.getRuntime().totalMemory();
   long difference = ( start - end ) / _SIZE;
   System.out.println( difference + " bytes used
   per object on average" );
   }
  }
  
  
  
    實際上,這種方法基本上正確了,但是By Tony Sintes疏忽了一點,就是僅僅Runtime.getRuntime().gc();並不能真正完成垃圾收集,也就是說實際上jvm的內存此時並不是穩定的。TW.WInGWit.cOM
  
    所以,只有當內存不再發生大的變動,或者說已經穩定,我們才可能說垃圾收集已經完成。
  
    如何才能真正確保基本完成了jvm的垃圾收集呢?實現這個功能的代碼如下:
  
  private static final Runtime s_runtime =
   Runtime.getRuntime ();
  private static long usedMemory ()
   {
   return s_runtime.totalMemory () -
   s_runtime.freeMemory ();
   }
  private static void runGC () throws Exception
   {
  long usedMem1 = usedMemory (), usedMem2 = Long.MAX_value;
  for (int i = 0; (usedMem1 < usedMem2) && (i < 500); ++ i)
   {
   s_runtime.runFinalization ();
   s_runtime.gc ();
   Thread.currentThread ().yield ();
   usedMem2 = usedMem1;
   usedMem1 = usedMemory ();
   }
   }
  
  
  
    runGC()可以幫我們真正的確定完成垃圾收集(准確的說,應該說是基本上完成)。
From:http://tw.wingwit.com/Article/program/Java/hx/201311/26455.html
    推薦文章
    Copyright © 2005-2013 電腦知識網 Computer Knowledge   All rights reserved.