Kamis, 23 Mei 2013

Heap



Stack dan Heap

·         Dalam java, dikenal 2 buah jenis memory, yaitu [1&2]:
1.      Stack (tempat local variable dan tumpukan method)
2.      Heap (tempat instance variable dan object)
·         Bila ada program berikut [1] :
Program xx
 1.  public class A {
 2.      B b1 = new B();
 3.      String s = "halo";
 4.      int i = 10;
 5.      
 6.      public static void main(String[] args) {
 7.          A a = new A();
 8.          a.myMethod();
 9.      }
10.     
11.      private void myMethod() {
12.          System.out.println(s);
13.      }
14.  }
class B {}
Yang terletak di stack :
1.  Method main()
2.  Method myMethod()
3.      Variable reference a (baris 7)
Yang terletak di heap :
1.      Variable reference b1 (baris 2)
2.      Variable reference s (baris 3)
3.      Variable i (baris 4)
4.      Object dari kelas B (baris 2)
5.      Object String dengan nilai “halo” (baris 3)
6.      Object dari kelas A (baris 7)

2. Garbage Collector

·         Pembahasan garbage collector ini dibatasi hanya pada object-object non String [2].
·         Garbage collector (GC) menyediakan solusi otomatis dalam memory management [2]. Pada kebanyakan kasus, GC membebaskan kita dari mengatur logic memory management dalam aplikasi [2].
·         Tugas utama GC adalah menyediakan free space pada heap sebanyak mungkin. Hal ini dilakukan dengan menemukan dan menghapus object pada heap yang sudah tidak direference oleh variable apapun [1&2]. Meskipun tugas utama GC adalah menyediakan free space pada heap sebanyak mungkin, tapi tidak ada jaminan bahwa di heap ada memory yang cukup untuk berjalannya program java [1&2].
·         Kapan GC berjalan ?  JVM memutuskan kapan menjalankan GC. Melalui program, kita dapat menyarankan JVM untuk menjalankan GC, akan tetapi yang memutuskan apakah GC perlu berjalan atau tidak tetaplah JVM (kita hanya dapat menyarankan saja!). Biasanya JVM akan menjalankan GC bila dirasa free memory sedang rendah [2].
·         Kita tidak dapat mengetahui algoritma yang digunakan dalam GC [2].
·         Apakah java dapat ”run out of memory” ? Ya, program java dapat mengalami run out of memory, hal ini terjadi karena terlalu banyak object “hidup” di dalam heap.

2.1 Kode program yang membuat suatu object layak untuk dihapus

·         Kapan suatu object memenuhi syarat untuk dihapus ? Suatu object layak untuk dihapus bila tidak ada thread yang dapat mengakses object ini [2].
·         Setidaknya ada 4 hal yang membuat suatu object layak dihapus, yaitu [2] :
1.      Memberikan nilai null pada variable reference.
2.      Mengassign suatu variable reference dengan object lain.
3.      Object yang direference oleh local variable.
4.      Isolating reference
·         Contoh memberikan nilai null pada variable reference [1] :
Program 01
public class GC1
{
      public static void main(String[] args)
      {
            Object o = new Object();
            o = null; //memberi nilai null pada reference variable
      }
}
·         Contoh mengassign variable reference dengan object lain [1]:
Program 02
public class GC2
{
      public static void main(String[] args)
      {
            Object o1 = new Object();
            Object o2 = new Object();
            o2 = o1; //mengassign dengan object lain
      }
}
·         Suatu object yang hanya direference oleh local variable akan memenuhi syarat untuk di hapus oleh GC begitu method (tempat local varible) tersebut selesai dijalankan [1&2].
Contoh [1]:
Program 03
public class GC3
{
      public static void main(String[] args)
      {
            myMethod();
      }
     
      public static void myMethod()
      {
            Object o = new Object();
            /*
             * object yang direference oleh local variable o di atas
             * memenuhi syarat untuk dihapus oleh GC begitu method
             * ini selesai dijalankan.
             */
            //do something!!
      }
}
·         Isolating reference adalah suatu bentuk hubungan antar object yang memenuhi syarat untuk dihapus oleh GC meski object-object tersebut ada yang mereferensi [1&2].
Contoh [2] :
Program 04
class X
{
      X x;
}
public class GC4
{
      public static void main(String[] args)
      {
            X x1 = new X(); //membuat object
            X x2 = new X(); //membuat object
           
            /*
             * 2 statement di bawah membuat "circular reference"
             */
            x1.x = x2;
            x2.x = x1;
           
            /*
             * 2 statement di bawah membuat dua buah object
             * kelas X yang dibuat diatas tidak dapat di
             * reference oleh thread manapun, meskupun
             * kedua object itu saling membuat "circular
             * reference"
             */
            x1 = null;
            x2 = null;
      }
}

2.2 Meminta JVM melakukan GC

·         Melalui kode program, kita dapat meminta agar JVM melakukan GC. JVM akan berusaha memenuhi permintaan kita, meski tidak ada jaminan permintaan kita akan terpenuhi [1&2].
·         Ada 2 cara untuk meminta JVM melakukan GC, yaitu melalui [2]:
1.  System.gc() (lebih direkomendasikan dari pada cara ke dua)
2.      Method gc() dari suatu instance Runtime
·         Contoh penggunaan method gc() dari suatu instance Runtime [2] :
Program 05
package garbageCollector;
import java.util.Date;
public class GC5
{
      public static void main(String[] args)
      {
            Runtime rt = Runtime.getRuntime();
           
            System.out.println("Total memory JVM = " +
                        rt.totalMemory());
            System.out.println("Free memory sebelum proses = " +
                        rt.freeMemory());
           
            //--------------------------proses
            Date d = null;
            for(int i = 0; i < 10000; i++)
            {
                  d = new Date();
                  d = null;
            }
            //--------------------------------
           
            System.out.println("Free memory setelah proses = " +
                        rt.freeMemory());
            rt.gc(); // Request melakukan GC!!
            System.out.println("Free memory setelah GC = " +
                        rt.freeMemory());
      }
}
Program di atas akan menghasilkan :
Total memory JVM = 2031616
Free memory sebelum proses = 1862240
Free memory setelah proses = 1617528
Free memory setelah GC = 1917448
·         Contoh penggunaan System.gc() [2] :
Program 06
package garbageCollector;
import java.util.Date;
public class GC6
{
      public static void main(String[] args)
      {
            Runtime rt = Runtime.getRuntime();
           
            System.out.println("Total memory JVM = " +
                        rt.totalMemory());
            System.out.println("Free memory sebelum proses = " +
                        rt.freeMemory());
           
            //--------------------------proses
            Date d = null;
            for(int i = 0; i < 10000; i++)
            {
                  d = new Date();
                  d = null;
            }
            //--------------------------------
           
            System.out.println("Free memory setelah proses = " +
                        rt.freeMemory());
            System.gc(); // Request melakukan GC!!
            System.out.println("Free memory setelah GC = " +
                        rt.freeMemory());
      }
}
Program di atas akan menghasilkan :
Total memory JVM = 2031616
Free memory sebelum proses = 1862240
Free memory setelah proses = 1617528
Free memory setelah GC = 1917448

2.3 Method finalize()

·         Java menyediakan suatu mekanisme untuk menjalankan suatu kode sebelum suatu object dihapus oleh GC. Method tersebut terletak pada method finalize dari yang diturunkan dari kelas Object [2] .
·         Karena kita tidak dapat mengantungkan pada GC untuk menghapus suatu object, maka kode yang terdapat di method finalize tidak dijamin akan dijalankan [2].
·         Method finalize maksimal dijalankan 1 kali (yang berarti dapat tidak dijalankan) [2].
·         Contoh [1]
Program 07
class Y
{
      private String nama = null;
     
      Y(String nama)
      {
            this.nama = nama;
      }
     
      public void finalize()
      {
            System.out.println(nama + " dihapus");
      }
}
public class GC7
{
      public static void main(String[] args)
      {
            Y y1 = new Y("Hallo");
            Y y2 = new Y("ini");
            Y y3 = new Y("percobaan");
            Y y4 = new Y("method");
            Y y5 = new Y("finalize");
           
            y1 = null;
            y2 = null;
            y3 = null;
            y4 = null;
            y5 = null;
           
            System.gc();
      }
}
Program di atas akan menghasilkan :
finalize dihapus
method dihapus
percobaan dihapus
ini dihapus
Hallo dihapus

Heap pada java



Stack dan Heap

·         Dalam java, dikenal 2 buah jenis memory, yaitu [1&2]:
1.      Stack (tempat local variable dan tumpukan method)
2.      Heap (tempat instance variable dan object)
·         Bila ada program berikut [1] :
Program xx
 1.  public class A {
 2.      B b1 = new B();
 3.      String s = "halo";
 4.      int i = 10;
 5.      
 6.      public static void main(String[] args) {
 7.          A a = new A();
 8.          a.myMethod();
 9.      }
10.     
11.      private void myMethod() {
12.          System.out.println(s);
13.      }
14.  }
class B {}
Yang terletak di stack :
1.  Method main()
2.  Method myMethod()
3.      Variable reference a (baris 7)
Yang terletak di heap :
1.      Variable reference b1 (baris 2)
2.      Variable reference s (baris 3)
3.      Variable i (baris 4)
4.      Object dari kelas B (baris 2)
5.      Object String dengan nilai “halo” (baris 3)
6.      Object dari kelas A (baris 7)

2. Garbage Collector

·         Pembahasan garbage collector ini dibatasi hanya pada object-object non String [2].
·         Garbage collector (GC) menyediakan solusi otomatis dalam memory management [2]. Pada kebanyakan kasus, GC membebaskan kita dari mengatur logic memory management dalam aplikasi [2].
·         Tugas utama GC adalah menyediakan free space pada heap sebanyak mungkin. Hal ini dilakukan dengan menemukan dan menghapus object pada heap yang sudah tidak direference oleh variable apapun [1&2]. Meskipun tugas utama GC adalah menyediakan free space pada heap sebanyak mungkin, tapi tidak ada jaminan bahwa di heap ada memory yang cukup untuk berjalannya program java [1&2].
·         Kapan GC berjalan ?  JVM memutuskan kapan menjalankan GC. Melalui program, kita dapat menyarankan JVM untuk menjalankan GC, akan tetapi yang memutuskan apakah GC perlu berjalan atau tidak tetaplah JVM (kita hanya dapat menyarankan saja!). Biasanya JVM akan menjalankan GC bila dirasa free memory sedang rendah [2].
·         Kita tidak dapat mengetahui algoritma yang digunakan dalam GC [2].
·         Apakah java dapat ”run out of memory” ? Ya, program java dapat mengalami run out of memory, hal ini terjadi karena terlalu banyak object “hidup” di dalam heap.

2.1 Kode program yang membuat suatu object layak untuk dihapus

·         Kapan suatu object memenuhi syarat untuk dihapus ? Suatu object layak untuk dihapus bila tidak ada thread yang dapat mengakses object ini [2].
·         Setidaknya ada 4 hal yang membuat suatu object layak dihapus, yaitu [2] :
1.      Memberikan nilai null pada variable reference.
2.      Mengassign suatu variable reference dengan object lain.
3.      Object yang direference oleh local variable.
4.      Isolating reference
·         Contoh memberikan nilai null pada variable reference [1] :
Program 01
public class GC1
{
      public static void main(String[] args)
      {
            Object o = new Object();
            o = null; //memberi nilai null pada reference variable
      }
}
·         Contoh mengassign variable reference dengan object lain [1]:
Program 02
public class GC2
{
      public static void main(String[] args)
      {
            Object o1 = new Object();
            Object o2 = new Object();
            o2 = o1; //mengassign dengan object lain
      }
}
·         Suatu object yang hanya direference oleh local variable akan memenuhi syarat untuk di hapus oleh GC begitu method (tempat local varible) tersebut selesai dijalankan [1&2].
Contoh [1]:
Program 03
public class GC3
{
      public static void main(String[] args)
      {
            myMethod();
      }
     
      public static void myMethod()
      {
            Object o = new Object();
            /*
             * object yang direference oleh local variable o di atas
             * memenuhi syarat untuk dihapus oleh GC begitu method
             * ini selesai dijalankan.
             */
            //do something!!
      }
}
·         Isolating reference adalah suatu bentuk hubungan antar object yang memenuhi syarat untuk dihapus oleh GC meski object-object tersebut ada yang mereferensi [1&2].
Contoh [2] :
Program 04
class X
{
      X x;
}
public class GC4
{
      public static void main(String[] args)
      {
            X x1 = new X(); //membuat object
            X x2 = new X(); //membuat object
           
            /*
             * 2 statement di bawah membuat "circular reference"
             */
            x1.x = x2;
            x2.x = x1;
           
            /*
             * 2 statement di bawah membuat dua buah object
             * kelas X yang dibuat diatas tidak dapat di
             * reference oleh thread manapun, meskupun
             * kedua object itu saling membuat "circular
             * reference"
             */
            x1 = null;
            x2 = null;
      }
}

2.2 Meminta JVM melakukan GC

·         Melalui kode program, kita dapat meminta agar JVM melakukan GC. JVM akan berusaha memenuhi permintaan kita, meski tidak ada jaminan permintaan kita akan terpenuhi [1&2].
·         Ada 2 cara untuk meminta JVM melakukan GC, yaitu melalui [2]:
1.  System.gc() (lebih direkomendasikan dari pada cara ke dua)
2.      Method gc() dari suatu instance Runtime
·         Contoh penggunaan method gc() dari suatu instance Runtime [2] :
Program 05
package garbageCollector;
import java.util.Date;
public class GC5
{
      public static void main(String[] args)
      {
            Runtime rt = Runtime.getRuntime();
           
            System.out.println("Total memory JVM = " +
                        rt.totalMemory());
            System.out.println("Free memory sebelum proses = " +
                        rt.freeMemory());
           
            //--------------------------proses
            Date d = null;
            for(int i = 0; i < 10000; i++)
            {
                  d = new Date();
                  d = null;
            }
            //--------------------------------
           
            System.out.println("Free memory setelah proses = " +
                        rt.freeMemory());
            rt.gc(); // Request melakukan GC!!
            System.out.println("Free memory setelah GC = " +
                        rt.freeMemory());
      }
}
Program di atas akan menghasilkan :
Total memory JVM = 2031616
Free memory sebelum proses = 1862240
Free memory setelah proses = 1617528
Free memory setelah GC = 1917448
·         Contoh penggunaan System.gc() [2] :
Program 06
package garbageCollector;
import java.util.Date;
public class GC6
{
      public static void main(String[] args)
      {
            Runtime rt = Runtime.getRuntime();
           
            System.out.println("Total memory JVM = " +
                        rt.totalMemory());
            System.out.println("Free memory sebelum proses = " +
                        rt.freeMemory());
           
            //--------------------------proses
            Date d = null;
            for(int i = 0; i < 10000; i++)
            {
                  d = new Date();
                  d = null;
            }
            //--------------------------------
           
            System.out.println("Free memory setelah proses = " +
                        rt.freeMemory());
            System.gc(); // Request melakukan GC!!
            System.out.println("Free memory setelah GC = " +
                        rt.freeMemory());
      }
}
Program di atas akan menghasilkan :
Total memory JVM = 2031616
Free memory sebelum proses = 1862240
Free memory setelah proses = 1617528
Free memory setelah GC = 1917448

2.3 Method finalize()

·         Java menyediakan suatu mekanisme untuk menjalankan suatu kode sebelum suatu object dihapus oleh GC. Method tersebut terletak pada method finalize dari yang diturunkan dari kelas Object [2] .
·         Karena kita tidak dapat mengantungkan pada GC untuk menghapus suatu object, maka kode yang terdapat di method finalize tidak dijamin akan dijalankan [2].
·         Method finalize maksimal dijalankan 1 kali (yang berarti dapat tidak dijalankan) [2].
·         Contoh [1]
Program 07
class Y
{
      private String nama = null;
     
      Y(String nama)
      {
            this.nama = nama;
      }
     
      public void finalize()
      {
            System.out.println(nama + " dihapus");
      }
}
public class GC7
{
      public static void main(String[] args)
      {
            Y y1 = new Y("Hallo");
            Y y2 = new Y("ini");
            Y y3 = new Y("percobaan");
            Y y4 = new Y("method");
            Y y5 = new Y("finalize");
           
            y1 = null;
            y2 = null;
            y3 = null;
            y4 = null;
            y5 = null;
           
            System.gc();
      }
}
Program di atas akan menghasilkan :
finalize dihapus
method dihapus
percobaan dihapus
ini dihapus
Hallo dihapus