Rabu, 27 Oktober 2010

Inheritance dan Polymorphism

Pada dasarnya kita sebagai manusia sudah terbiasa untuk melihat objek yang berada di sekitar kita tersusun secara hierarki berdasarkan class-nya masing-masing. Dari sini kemudian timbul suatu konsep tentang pewarisan yang merupakan suatu proses dimana suatu class diturunkan dari class lainnya sehingga ia mendapatkkan ciri atau sifat dari class tersebut.
Dari hirarki di atas dapat dilihat bahwa, semakin ke bawah, class akan semakin bersifat spesifik. Misalnya, sebuah Class mamalia memiliki seluruh sifat yang dimiliki oleh binatang, demikian halnya juga anjing, kucing dan monyet memiliki seluruh sifat yang diturunkan dari class mamalia. Dengan konsep ini, karakteristik yang dimiliki oleh class binatang cukup didefinisikan dalam class binatang saja. Class mamalia tidak perlu mendefinisikan ulang apa yang telah dimiliki oleh class binatang, karena sebagai class turunannya, ia akan mendapatkan karakteristik dari class binatang secara otomatis. Demikian juga dengan class anjing, kucing dan monyet, hanya perlu mendefinisikan karakteristik yang spesifik dimiliki oleh class-nya masing-masing. Dengan memanfaatkan konsep pewarisan ini dalam pemrograman, maka hanya perlu mendefinisikan karakteristik yang lebih umum akan didapatkan dari class darimana ia diturunkan.

Penurunan sifat tersebut dalam Bahasa Pemrograman Java disebut dengan Inheritance yaitu satu dalam Pilar Dasar OOP (Object Oriented Programing), yang dalam implementasinya merupakan sebuah hubungan “adalah bagian dari” atau “is a relationship” object yang diinherit (diturunkan).
Latar belakang diperlukannya suatu inheritance dalam pemrograman java adalah untuk menghindari duplikasi object baik itu field, variable maupun methode yang sebenarnya merupakan object yang bisa diturunkan dari hanya sebuah class. Jadi inheritance bukan sebuah Class yang di inherit oleh sebuah Literial, tapi lebih menunjukkan ke hubungan antar object itu sendiri.
Sedangkan suatu kemampuan dari sebuah object untuk membolehkan mengambil beberapa bentuk yang berbeda agar tidak terjadi duplikasi object kita kenal sebagai polymorphism.
Antara penurununan sifat (inheritance) maupun polymorphism merupakan konsep yang memungkinkan digunakannya suatu interface yang sama untuk memerintah objek agar melakukan aksi atau tindakan yang mungkin secara prinsip sama namun secara proses berbeda. Dalam konsep yang lebih umum sering kali polymorphism disebut dalam istilah tersebut
Dalam Java, semua class termasuk class yang membangun Java API adalah subclasses dari superclass Object. Contoh hirarki class diperlihatkan di bawah ini. Beberapa class di atas class utama dalam hirarki class dikenal sebagai superclass. Sementara beberapa class di bawah class pokok dalam hirarki class dikenal sebagai subclass dari class tersebut.
Pewarisan adalah keuntungan besar dalam pemrograman berbasis object karena suatu sifat atau method didefinisikan dalam superclass, sifat ini secara otomatis diwariskan dari semua subclasses. Jadi, Kita dapat menuliskan kode method hanya sekali dan mereka dapat digunakan oleh semua subclass. Subclass hanya perlu mengimplementasikannya perbedaan sendiri dan induknya.
Secara Terminologi asing pewarisan disebut juga inheritance. Secara gamblang, pewarisan berarti sebuah kelas mewarisi state dan behaviour dari kelas lain. Sebagai contoh, sebuah kelas Anjing akan mewarisi state dan behaviour dari kelas Mamalia. Begitu juga dengan kelas Monyet. Kelas Anjing dan Monyet disebut subkelas, atau kelas anak, dari kelas Mamalia, yang disebut superkelas, atau kelas induk.
Seluruh subkelas akan mewarisi (inherits) state dan behaviour dari superkelasnya. Dengan begitu, semua subkelas dari superkelas yang sama akan memiliki state dan behaviour yang sama. Namun, masing-masing subkelas bisa menambah sendiri state atau behaviournya. Misalkan, pada kelas Mamalia tidak terdapat variable BerkukuTajam, namun subkelas Monyet memiliki variabel tersebut. Contoh lain misalnya kelas Anjing tidak memiliki metode MakanMenggunakanTangan, namun Monyet memiliki metode itu.
Dalam kasus tertentu subkelas mungkin memiliki implementasi behaviour yang berbeda dengan superkelasnya. Hal seperti ini disebut override. Contohnya subkelas SepedaBalap memiliki implementasi metode ubahGigi yang berbeda dengan implementasi metode tersebut pada superkelas Sepeda.
Tingkat pewarisan tidak hanya terbatas pada dua tingkatan. Dari contoh di atas, kita bisa saja membuat subkelas dari kelas SepedaBalap, dan seterusnya. Kita bisa terus memperpanjang tingkat pewarisan ini sepanjang yang kita butuhkan. Dengan begitu, subkelas-subkelas yang dibuat akan lebih khusus dan lebih terspesialisasi.
Namun terdapat batasan pewarisan dalam Java yang disebut single inheritance. Artinya sebuah kelas hanya dapat mewarisi sifat dari satu dan hanya satu superkelas saja. Dalam beberapa bahasa pemrograman berorientasi objek lain, yang berlaku adalah multiple inheritance. Artinya sebuah kelas dapat mewarisi sifat dari beberapa superkelas sekaligus.
Dalam Java, terdapat kelas Object yang merupakan superkelas dari semua kelas dalam Java, baik yang builtin ataupun yang kita buat sendiri, lansung maupun tidak langsung. Karena itu sebuah variabel bertipe Object akan dapat menyimpan referensi ke objek apapun dalam bahasa Java. Kelas Object ini memiliki behaviour yang dibutuhkan semua objek untuk dapat dijalankan di Java Virtual Machine. Sebagai contoh, semua kelas mewarisi metode toString dari kelas Object, yang mengembalikan representasi String dari objek tersebut.
Manfaat penggunaan konsep pewarisan antara lain:
1. Kita dapat menggunakan kembali kelas-kelas yang kita buat (sebagai superkelas) dan membuat kelas-kelas baru berdasar superkelas tersebut dengan karakteristik yang lebih khusus dari behaviour umum yang dimiliki superkelas.
2. Kita dapat membuat superkelas yang hanya mendefinisikan behaviour namun tidak memberi implementasi dari metode-metode yang ada. Hal ini berguna jika kita ingin membuat semacam template kelas. Kelas semacam ini disebut kelas abstrak, karena behaviournya masih abstrak dan belum diimplementasikan. Subkelas-subkelas dari kelas semacam ini, yang disebut kelas konkret, mengimplementasikan behaviour abstrak tersebut sesuai dengan kebutuhan masing-masing.
Sedikit penjelasan mengenai kelas abstrak, kelas ini bisa memiliki hanya satu atau lebih metode abstrak. Subkelas dari kelas ini bertanggung jawab untuk memberikan implementasi untuk metode-metode abstrak tersebut.
Sebagai akibat dari keberadaan metode abstrak ini, kelas abstrak tidak dapat diinstanskan (dibuatkan instansnya) atau digunakan untuk menciptakan sebuah objek dari kelas tersebut.
Class dapat didefinisikan dengan referensi pada class yang lain yang telah terdefinisi. Inheritance merupakan pewarisan atribut dan method pada sebuah class yang diperoleh dari class yang telah terdefinisi tersebut. Setiap subclass akan mewarisi state ( variabel-variabel ) dan behaviour ( methodmethod ) dari superclass-nya. Subclass kemudian dapat menambahkan state dan behaviour baru yang spesifik dan dapat pula memodifikasi ( override ) state dan behaviour yang diturunkan oleh superclass-nya.
Keuntungan dari inheritance adalah Subclass menyediakan state/behaviour yang spesifik yang membedakannya dengan superclass, hal ini akan memungkinkan programmer Java untuk menggunakan ulang source code dari
superclass yang telah ada. Programmer Java dapat mendefinisikan superclass khusus yang bersifat generik, yang disebut abstract class, untuk mendefinisikan
class dengan behaviour dan state secara umum.
Istilah dalam inheritance yang perlu diperhatikan :
 Extends
Keyword ini harus kita tambahkan pada definisi class yang menjadi subclass.
 Superclass
Superclass digunakan untuk menunjukkan hirarki class yang berarti class dasar dari subclass/class anak.
 Subclass
Subclass adalah class anak atau turunan secara hirarki dari superclass.
 Super
Keyword ini digunakan untuk memanggil konstruktor dari superclass atau menjadi variabel yang mengacu pada superclass. Methode Overriding. Pendefinisian ulang method yang sama pada subclass. Dalam inheritance, method overriding berbeda dengan method overloading. Kalau method overriding adalah
Mendefinisikan kembali method yang sama, baik nama method maupun signature atau parameter yang diperlukan dalam subclass, kalau method overloading adalah mendefinisikan method yang memiliki nama yang sama, tetapi dengan signature yang berbeda dalam definisi class yang sama.
Polymorphism berasal dari bahasa Yunani yang berarti banyak bentuk. Dalam PBO, konsep ini memungkinkan digunakannya suatu interface yang sama untuk memerintah objek agar melakukan aksi atau tindakan yang mungkin secara prinsip sama namun secara proses berbeda. Dalam konsep yang lebih umum sering kali polymorphism disebut dalam istilah satu interface banyak aksi.
Contoh yang konkrit dalam dunia nyata yaitu mobil. Mobil yang ada dipasaran terdiri atas berbagai tipe dan berbagai merk, namun semuanya memiliki interface kemudi yang sama, seperti: stir, tongkat transmisi, pedal gas dan rem. Jika seseorang dapat mengemudikan satu jenis mobil saja dari satu merk tertentu, maka orang itu akan dapat mengemudikan hamper semua jenis mobil yang ada, karena semua mobil tersebut menggunakan interface yang sama. Harus diperhatikan disini bahwa interface yang sama tidak berarti cara kerjanya juga sama. Missal pedal gas, jika ditekan maka kecepatan mobil akan meningkat, tapi bagaiman proses peningkatan kecepatan ini dapat berbeda-beda untuk setiap jenis mobil.
Polimorfisme adalah kemampuan dari sebuah object untuk membolehkan mengambil beberapa bentuk yang berbeda. Secara harfiah, “poli” berarti banyak sementara “morph” berarti bentuk.
Menunjuk pada contoh sebelumnya pada pewarisan, kita lihat bahwa object SuperHero dapat juga menjadi object FlyingSuperHero atau object UnderwaterSuperHero.
Polimorfisme yang berarti satu objek dengan banyak bentuk yang berbeda, adalah konsep sederhana dalam bahasa pemrograman berorientasi objek yang berarti kemampuan dari suatu variabel referensi objek untuk memiliki aksi berbeda bila method yang sama dipanggil, dimana aksi method tergantung dari tipe objeknya. Kondisi yang harus dipenuhi supaya polimorfisme dapat diimplementasikan adalah :
1. Method yang dipanggil harus melalui variabel dari basis class atau superclass.
2. Method yang dipanggil harus juga menjadi method dari basis class.
3. Signature method harus sama baik pada superclass maupun subclass.
4. Method access attribute pada subclass tidak boleh lebih terbatas daribasis class.
Hal yang sangat tidak efisien adalah terjadinya kerangkapan atau duplikat dalam syntax program. Untuk menghindari hal yang demikian dalam Program Berorientasi Object Java, sesuai dengan sifat penurunan dari sebuah inheritance dapat menghindari duplikasi object baik itu field, variable, maupun methode yang sebenarnya bisa diturunkan dari sebuah class.
Perhatikan perbedaan 2 class berikut!
Inheritance dalam Sebuah SalesPersonEmpClass.
public class SalesPersonEmpClass
{
private string empId;
private string empName;
private decimal numOfSales;
public string EmpId
{
get {return this.empId;}
set {this.empId = value;}
}
public string EmpName
{
get {return this.empName;}
set {this.empName = value;}
}
public decimal NumOfSales
{
get {return this.numOfSales;}
set {this.numOfSales = value;}
}
public decimal CalculateMonthlySales()
{
if (this.empId == "1")
{
return (this.numOfSales * 10);
}
else if (this.empId == "2")
{
return (this.numOfSales * 20);
}
}
}

public class TopManagementEmpClass
{
private string empId;
private string empName;
private decimal amtMonthlyBonus;
public string EmpId
{
get { return this.empId; }
set { this.empId = value; }
}
public string EmpName
{
get { return this.empName; }
set { this.empName = value; }
}
public decimal AmtMonthlyBonus
{
get { return this.amtMonthlyBonus; }
set { this.amtMonthlyBonus = value; }
}
public decimal CalculateMonthlyBonus()
{
if (this.empId == "1")
{
return (this.amtMonthlyBonus * 10);
}
else if (this.empId == "2")
{
return (this.amtMonthlyBonus * 20);
}
}
}
Dari kedua class tersebut, sudah terdapat define private variable dan property-propertynya, sehingga kalau kita lihat per Class tanpa melihat Class yang lain hal ini sudah benar menurut kaidah pemrograman yang berorientasi pada object. Tapi, kalau kita lihat keseluruhan Class maka terdapat duplikasi pada kedua variable empId dan variable empName dan hal inilah yang tidak dibenarkan.
Selanjutnya dalam proses kita bisa menjadikan bagian-bagian yang lebih kecil dan spesifik :
1. Membuat EmployeeBaseClass yang akan diturunkan ke kelas SalesPersonEmpClass dan TopManagementEmpClass.
2. Membuat Class untuk SalesPersonEmpClass
3. Membuat Class untuk TopManagementEmpClass.
Berikut adalah ketiga class yang sudah disesuaikan untuk kepentingan proses inheritance dari beberapa class di atas :
public class EmployeeBaseClass
{
protected string empId;
protected string empName;
}

public class SalesEmp:EmployeeBaseClass
{
private decimal numOfSales;
public decimal NumOfSales
{
get { return this.numOfSales; }
set { this.numOfSales = value; }
}
public decimal CalculateMonthlySales()
{
if (this.empId == "1")
{
return (this.numOfSales * 10);
}
else if (this.empId == "2")
{
return (this.numOfSales * 20);
}
}
}

public class TopManagementEmp:EmployeeBaseClass
{
private decimal amtMonthlyBonus;
public decimal AmtMonthlyBonus
{
get { return this.amtMonthlyBonus; }
set { this.amtMonthlyBonus = value; }
}
public decimal CalculateMonthlyBonus()
{
if (this.empId == "1")
{
return (this.amtMonthlyBonus * 10);
}
else if (this.empId == "2")
{
return (this.amtMonthlyBonus * 20);
}
}
}
Dari proses class tersebut kita dapat melihat proses inheritance yang semudah itu, yaitu proses inheritance [SalesEmp:EmployeeBaseeClass] dan [TopManagementEmployeesBaseClass]. Hal yang munkin sulit adalah bagaimana kita memutuskan utnuk membagi bagian-bagian itu menjadi bagian yang lebih kecil dan saling berhubungan. Sehingga bisa diturunkan ke bagian yang lain tanpa terlepas dari kaedah hubungan “Bagian Dari”.

Inheritance merupakan satu dalam Pilar Dasar OOP (Object Oriented Programing), yang dalam implementasinya sebagai sebuah hubungan “adalah bagian dari” atau “is a relationship” object yang diinherit (diturunkan).
Latar belakang diperlukannya suatu inheritance dalam pemrograman java adalah untuk menghindari duplikasi object baik itu field, variable maupun methode yang sebenarnya merupakan object yang bisa diturunkan dari hanya sebuah class. Jadi inheritance bukan sebuah Class yang di inherit oleh sebuah Literial, tapi lebih menunjukkan ke hubungan antar object itu sendiri.
Sedangkan polimorfisme yang berarti satu objek dengan banyak bentuk yang berbeda, adalah konsep sederhana dalam bahasa pemrograman berorientasi objek yang berarti kemampuan dari suatu variabel referensi objek untuk memiliki aksi berbeda bila method yang sama dipanggil, dimana aksi method tergantung dari tipe objeknya. Kondisi yang harus dipenuhi supaya polimorfisme dapat diimplementasikan adalah : Method yang dipanggil harus melalui variabel dari basis class atau superclass. Method yang dipanggil harus juga menjadi method dari basis class. Signature method harus sama baik pada superclass maupun subclass. Method access attribute pada subclass tidak boleh lebih terbatas dari basis class.
Dalam membuat program berorientasi java perlu diperhatikan penurunan sifat agar tidak terulang atau terduplikasi dari class atau subclass yang sudah ada, sehingga kerja syntax program dapat lebih efisien dan cara pemahaman bagi operatornya juga mudah.
Program berikut ini mungkin akan tampak aneh. Mengapa kita secara sengaja melupakan tipe dari sebuah object ? Ini semua dapat terjadi bila kita melakukan upcast, dan menjadikannya kelihatan seperti kalau tune() secara langsung mengambil handle dari Wind sebagai sebuah argumen. Ini semua membuat sesuatu yang mendasar : Kalau kita melakukannya, kita harus menuliskan tune() yang baru untuk setiap Instrument didalam system kita. Anggap saja kita mengikuti alasan ini dan menambahkan instrument Stringed dan Brass :
//: Music2.java
// Overloading instead of upcasting

class Note2 {
private int value;
private Note2(int val) { value = val; }
public static final Note2
middleC = new Note2(0),
cSharp = new Note2(1),
cFlat = new Note2(2);
} // Etc.

class Instrument2 {
public void play(Note2 n) {
System.out.println(\"Instrument2.play()\");
}
}

class Wind2 extends Instrument2 {
public void play(Note2 n) {
System.out.println(\"Wind2.play()\");
}
}

class Stringed2 extends Instrument2 {
public void play(Note2 n) {
System.out.println(\"Stringed2.play()\");
}
}

class Brass2 extends Instrument2 {
public void play(Note2 n) {
System.out.println(\"Brass2.play()\");
}
}

public class Music2 {
public static void tune(Wind2 i) {
i.play(Note2.middleC);
}
public static void tune(Stringed2 i) {
i.play(Note2.middleC);
}
public static void tune(Brass2 i) {
i.play(Note2.middleC);
}
public static void main(String[] args) {
Wind2 flute = new Wind2();
Stringed2 violin = new Stringed2();
Brass2 frenchHorn = new Brass2();
tune(flute); // No upcasting
tune(violin);
tune(frenchHorn);
}
} ///:~
Kode diatas dapat dijalankan, tetapi disana ada kekurangan terbesar. Kita harus menuliskan metoda tipe yang spesifik untuk setiap class Instrument2 yang baru kita tambahkan. Ini semua berarti makin banyak kode yang akan kita tulis, tetapi juga berarti kalau kita ingin menambahkan sebuah metoda baru seperti tune() atau sebuah tipe baru dari Instrument, kita mendapatkan kalau perkerjaan kita makin banyak. Dengan menambahkan fakta bahwa kompiler tidak akan memberikan pesan-pesan kesalahan kalau kita lupa meng overload salah satu dari metoda-metoda kita dan seluruh proses pekerjaan dengan tipe menjadi tidak dapat ditangani.
Bukankah dapat menjadi lebih menyenangkan kalau kita hanya menuliskan satu metoda saja yang dapat mengambil class asal sebagai argumennya, dan bukan dari semua class-class turunannya. Itulah memang lebih memudahkan bila kita melupakan adanya class-class turunan, dan menuliskan kode yang hanya berkomunikasi dengan class asal?
Itulah apa yang disediakan oleh polymorphism. Walau bagaimanapun kebanyakan programmer (yang berasal dari latar belakang prosedural) mempunyai sedikit kesulitan untuk beradaptasi dengan polymorphism.
Kesimpulan
Dengan polymorphism pekerjaan seorang programmer dapat dimudahkan dengan menuliskan kode yang lebih sedikit. Untuk mengakses class-class turunan tidak dibutuhkan penulisan kode yang berlainan.

Tidak ada komentar:

Posting Komentar

 

Design By:
SkinCorner