Saturday, December 24, 2016

Bab 7. Visual Basic .NET Belajar Dari Contoh



7. Pemrograman Berbasis Objek







Pengantar

Pada bab ini, akan dijelaskan bagaimana menciptakan dan menggunakan kelas dan objek; Inilah topik pemrograman berbasis objek. Bab 8 dan Bab 9 akan mengenalkan pewarisan dan polimorfisme, dua teknik kunci yang memampukan pemrograman berorientasi objek.


Mengimplementasikan Tipe Data Abstrak Menggunakan Kelas
Kelas dalam Visual Basic memfasilitas penciptaan tipe data, yang dinamakan dengan tipe data abstrak (ADT, abstract data types), dimana implementasinya disembunyikan dari klien atau pengguna. Masalah yang sering ditemui dalam bahasa pemrograman prosedural adalah bahwa kode pengguna seringkali sangat bergantung pada kode implementasi; kode klien harus ditulis sehingga ia menggunakan anggota data spesifik dan harus ditulis-ulang jika terjadi perubahan. ADT dapat mengeliminasi masalah ini dengan menyediakan antarmuka bebas-implementasi kepada pengguna. Pencipta kelas dapat mengubah implementasinya tanpa harus mengubah pengguna kelas.

Sebelum mendiskusikan kelas lebih detil, akan dijelaskan bagaimana menambahkan kelas pada sebuah projek dalam Visual Studio. Sejauh ini, Anda telah familiar dengan penambahan module pada sebuah projek. Proses penambahan kelas hampir sama dengan penambahan modul pada sebuah projek. Untuk menambahkan sebuah kelas pada projek, Anda bisa mengklik kanan nama projek di dalam Solution Explorer kemudian pilih Add kemudian Class, seperti ditunjukkan pada Gambar 7.1.



Gambar 7.1 Penambahan kelas pada sebuah projek


Anda kemudian diminta untuk memasukkan nama kelas dalam bidang teks Name dan klik tombol Add. Perhatikan bahwa nama kelas (diakhiri dengan ekstensi file .vb) muncul di dalam Solution Explorer, seperti ditunjukkan pada Gambar 7.2.



Gambar 7.2 Pemberian nama kelas dan keberadaan kelas baru di dalam Solution Explorer


Aplikasi berikut memuat kelas CWaktu (kode 7.1) dan module modUjiWaktu (kode 7.2). Kelas CWaktu memuat informasi yang diperlukan dalam merepresentasikan waktu; module modUjiWaktu memuat metode Main, yang menggunakan sebuah instans dari kelas CWaktu untuk menjalankan aplikasi.

Pada kode 7.1, baris 4-5 memulai definisi kelas CWaktu, yang mengindikasikan bahwa kelas CWaktu mewarisi kelas Object (dari namespace System). Programer Visual Basic menggunakan pewarisan untuk menciptakan kelas dari kelas yang sudah ada. Katakunci Inherits (baris 5) yang diikuti dengan nama kelas Object mengindikasikan bahwa kelas CWaktu mewarisi semua komponen dari kelas Object. Jika programer tidak menyertakan baris 5, kompiler Visual Basic akan mencantumkannya secara eksplisit.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
' Kode 7.1: CWaktu.vb
' Merepresentasikan waktu dalam format 24-jam.

Public Class CWaktu
    Inherits Object

    ' mendeklarasikan nilai instans Integer untuk jam, menit, dan detik
    Private mJam As Integer ' 0 - 23
    Private mMenit As Integer ' 0 - 59
    Private mDetik As Integer ' 0 - 59

    ' Metode New adalah metode konstruktur CWaktu, yang menginisialisasi
    ' variabel instans dengan nol
    Public Sub New()
        SetWaktu(0, 0, 0)
    End Sub ' New

    ' menetapkan nilai waktu baru menggunakan waktu universal;
    ' melakukan pemeriksaan validitas pada data;
    ' menetapkan nilai tak-valid menjadi nol
    Public Sub SetWaktu(ByVal nilaiJam As Integer, _
        ByVal nilaiMenit As Integer, ByVal nilaiDetik As Integer)

        ' memeriksa jika jam berada di antara 0 dan 23, maka jam ditetapkan
        If (nilaiJam >= 0 AndAlso nilaiJam < 24) Then
            mJam = nilaiJam
        Else
            mJam = 0
        End If

        ' memeriksa jika menit berada di antara 0 dan 59, maka menit ditetapkan
        If (nilaiMenit >= 0 AndAlso nilaiMenit < 60) Then
            mMenit = nilaiMenit
        Else
            mMenit = 0
        End If

        ' memeriksa jika detik berada di antara 0 dan 59, maka detik ditetapkan
        If (nilaiDetik >= 0 AndAlso nilaiDetik < 60) Then
            mDetik = nilaiDetik
        Else
            mDetik = 0
        End If

    End Sub ' SetWaktu

    ' mengkonversi String menjadi format waktu-universal
    Public Function KeStringUniversal() As String
        Return String.Format("{0}:{1:D2}:{2:D2}", _
        mJam, mMenit, mDetik)
    End Function ' KeStringUniversal

    ' mengkonversi String dalam format-standar
    Public Function KeStringStandar() As String
        Dim sufiks As String = " SORE"
        Dim format As String = "{0}:{1:D2}:{2:D2}"
        Dim jamStandar As Integer

        ' menentukan waktu apakah PAGI atau SORE
        If mJam < 12 Then
            sufiks = " PAGI"
        End If

        ' mengkonversi dari format waktu-universal menjadi format waktu-standar
        If (mJam = 12 OrElse mJam = 0) Then
            jamStandar = 12
        Else
            jamStandar = mJam Mod 12
        End If

        Return String.Format(format, jamStandar, mMenit, _
         mDetik) & sufiks
    End Function ' KeStringStandar

End Class  ' CWaktu

Baris 4 dan 75 mangapit tubuh definisi kelas CTime dengan katakunci Class dan End Class. Sebagai contoh, kelas CWaktu memuat tiga variabel instans Integer, mJam, mMenit, dan mDetik (baris 8-10), yang merepresentasikan waktu dalam format waktu-universal (format 24-jam). Perhatikan bahwa variabel instans diberi prefiks ‘m’, sesuai dengan rekomendasi MSDN.

Katakunci Public dan Private adalah pemodifikasi akses anggota. Variabel instans atau metode dengan pemodifikasi akses Public dapat diakses manakala program memiliki sebuah referensi yang menunjuk ke objek CWaktu. Deklarasi atas variabel instans atau metode dengan pemodifikasi akses anggota Private membuatnya (variabel instans dan metode) hanya bisa diakses oleh metode-metode dari kelas tersebut. 

Baris 8-10 mendeklarasikan ketiga variabel instans Integer, mJam, mMenit, dan mJam, dengan pemodifikasi akses anggota Private, yang mengindikasikan bahwa ketiga variabel instans dari kelas ini hanya bisa diakses oleh semua anggota dari kelas tersebut. Ketika sebuah objek dari kelas tersebut mengenkapsulasi ketiga variabel semacam itu, hanya metode-metode dari objek kelas itu yang dapat mengakses variabel tersebut. Biasanya, variabel instans dideklarasikan Private, sedangkan metode dideklarasikan Public. Namun, adalah hal yang memungkinkan untuk memiliki metode Private dan variabel instans Public, seperti yang akan ditunjukkan nanti. Metode Private dikenal sebagai metode utilitas atau metode pembantu, karena metode semacam itu hanya dapat dipanggil oleh metode lain dari kelas yang sama, dan kegunaannya adalah untuk mendukung operasi metode lain. Penciptaan anggota data Public di dalam sebuah kelas jarang dijumpai dan berbahaya dalam dunia pemrograman, karena hal itu menyebabkan anggota data tidak aman dari penggunaan tak-valid oleh pengguna yang tak memiliki otoritas.

Metode akses dapat membaca atau menampilkan data. Kegunaan umum dari metode akses adalah untuk menguji kebenaran kondisi. Metode semacam itu seringkali dinamakan dengan metode predikat. Sebagai contoh, Anda bisa merancang metode predikat IsEmpty untuk sebuah kelas kontainer, sebuah kelas yang mempu menampung banyak objek, seperti senarai berantai (linked list), tumpukan (stack), atau antrian (queue). Metode ini menghasilkan nilai balik True jika kontainer kosong dan False jika sebaliknya. Sebuah program dapat menggunakan IsEmpty sebelum mencoba membaca item berikutnya dari objek kontainer. Sama halnya, sebuah program dapat memanggil metode predikat yang lain(misalnya, IsFull) sebelum mencoba menyisipkan item lain ke dalam objek kontainer.

Kelas CWaktu memuat beberapa metode Public, yaitu New (baris 14-16), SetWaktu (baris 21-45), KeStringUniversal (baris 48-51), dan KeStringStandar (baris 54-73). Keempatnya adalah metode Public (juga dikenal dengan layanan Public atau antarmuka Public) dari kelas. Klien, seperti module modUjiWaktu, menggunakan metode-metode tersebut untuk memanipulasi data yang disimpan di dalam objek kelas atau untuk meminta kelas untuk melakukan suatu layanan.

New adalah metode konstruktor. Suatu kelas dapat memiliki banyak konstruktor dengan nama sama, tetapi yang membedakan adalah  masing-masing memiliki parameter-parameter yang unik. Konstruktor adalah sebuah metode spesial yang menginisialisasi semua variabel instans objek. Instansiasi objek sebuah kelas menyebabkan pemanggilan terhadap metode konstruktor. Metode konstruktor ini (baris 14-16) kemudian memanggil SetWaktu dengan nilai-nilai mJam, mMenit, dan mDetik bernilai 0. Konstruktor bisa memiliki argumen tetapi tidak bisa memiliki nilai balik. Perbedaan utama antara konstruktor dan metode lainnya adalah bahwa konstruktor tidak dapat memberikan nilai balik. Karena alasan inilah, Visual Basic diimplementasikan sebagai prosedur Sub (karena prosedur Sub tidak bisa menghasilkan nilai balik). Secara umum, konstruktor adalah metode Public pada sebuah kelas.

Metode SetWaktu (baris 21-45) adalah metode Public yang menggunakan tiga argumen Integer untuk menetapkan waktu. Sebuah ekspresi kondisional menguji setiap argumen untuk menentukan apakah nilai berada dalam rentang tertentu. Sebagai contoh, nilai mJam harus lebih besar atau sama dengan 0 dan kurang dari 24, karena format waktu-universal merepresentasikan jam sebagai integer dari 0 sampai 23. Sama halnya, kedua nilai menit dan jam harus berada dalam rentang 0 dan 59. Sembarang nilai di luar rentang ini adalah nilai tak valid dan diberikan nilai default nol, paling tidak untuk memastikan bahwa objek CWaktu selalu memuat data valid.

Metode KeStringUniversal (baris 48-51) tidak mengambil argumen apapun dan menghasilkan nilai balik String dalam format waktu-universal, yang memuat enam dijit, dimana dua untuk jam, dua untuk menit, dan dua untuk detik. Misalnya, jika waktu adalah 1:30:07 SORE, metode KeStringUniversal akan menghasilkan String13:30:07”. Metode Format dipakai untuk mengkonfigurasi waktu universal. Baris 49 melewatkan “{0}:{1:D2}:{2:D2}” kepada string kendali format, yang mengindikasikan bahwa argumen 0 (argumen pertama setelah argumen String format) harus mengambil format default; dan argumen 1 dan 2 harus mengambil format D2 (format angka desimal basis 10 menggunakan dua dijit). Jadi, 8 akan dikonversi menjadi 08. Tanda titik koma yang memisahkan } dan { merepresentasikan titik koma yang memisahkan jam dari menit dan menit dari detik.

Metode KeStringStandar (baris 54-73) tidak mengambil argumen apapun dan menghasilkan nilai balik berupa sebuah String dalam format waktu-standar, yang memuat nilai-nilai mJam, mMenit, dan mDetik yang dipisahkan oleh titik koma dan diikuti dengan indikator PAGI dan SORE (misalnya, 1:27:06 SORE). Seperti metode KeStringUniversal, metode KeStringStandar memanggil metode Format dari kelas String untuk menjamin bahwa nilai Mmenit dan mDetik masing-masing sebagai dua dijit. Baris 60-69 menentukan pemformatan yang sesuai untuk jam.

Setelah mendefinisikan kelas, Anda dapat menggunakannya sebagai sebuah tipe dalam deklarasi sebagai

Dim matahariterbit As CWaktu ' referensi ke objek bertipe CWaktu

Nama kelas (CWaktu) adalah sebuah tipe. Kelas dapat menghasilkan banyak objek, sama seperti tipe data primitif (misalnya, Integer) dapat menghasilkan banyak variabel.

Module modUjiWaktu (kode 7.2) menggunakan sebuah instans dari kelas CWaktu. Metode Main (baris 8-33) mendeklarasikan dan menginisialisasi instans waktu dari kelas CWaktu (baris 9). Ketika objek diinstansiasi, katakunci New mengalokasikan memori dimana objek CWaktu akan disimpan, kemudian memanggil konstruktor CWaktu (metode New pada baris 14-16 pada kode 7.1) untuk menginisialisasi variabel instans dari objek CWaktu. Seperti disebutkan sebelumnya, konstruktor ini memanggil metode SetWaktu dari kelas CWaktu untuk menginisialisasi setiap variabel instans Private secara eksplisit dengan 0. Metode New kemudian menghasilkan nilai balik berupa sebuah referensi yang menunjuk ke objek yang baru saja diciptakan; referensi ini ditugasi objek waktu.

Perhatikan bahwa file UjiWaktu.vb tidak menggunakan katakunci Imports untuk mengimpor namespace yang memuat kelas CWaktu. Jika sebuah kelas berada di dalam namespace yang sama dan file .vb sebagai kelas yang menggunakannya, maka statemen Imports tidak diperlukan. Setiap kelas di dalam Visual Basic merupakan bagian dari namespace. Jika program tidak menspesifikasi namespace untuk sebuah kelas, maka kelas tersebut ditempatkan di dalam namespace default, yang menyertakan kelas-kelas terkompilasi.

Baris 10 mendeklarasikan sebuah referensi String, keluaran, yang akan menyimpan String untuk memuat hasil yang ditampilkan pada MessageBox. Baris 12-15 menugaskan waktu kepada keluaran dalam format waktu-universal (dengan memanggil metode KeStringUniversal dari kelas CWaktu) dan dalam format waktu-standar (dengan memanggil metode KeStringStandar dari kelas CWaktu).

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
' Kode 7.2: UjiWaktu.vb
' Mendemonstrasikan kelas CWaktu.

Imports System.Windows.Forms

Module modUjiWaktu

    Sub Main()
        Dim waktu As New CWaktu() ' memanggil konstruktor CWaktu
        Dim keluaran As String

        keluaran = "Waktu universal awal adalah: " & _
        waktu.KeStringUniversal() & vbCrLf & _
        "Waktu standar awal adalah: " & _
        waktu.KeStringStandar()

        waktu.SetWaktu(13, 27, 6) ' menetapkan waktu dengan valid

        keluaran &= vbCrLf & vbCrLf & _
          "Waktu universal setelah SetWaktu adalah: " & _
          waktu.KeStringUniversal() & vbCrLf & _
          "Waktu standar setelah SetWaktu adalah: " & _
          waktu.KeStringStandar()

        waktu.SetWaktu(99, 99, 99) ' menetapkan waktu dengan tak-valid

        keluaran &= vbCrLf & vbCrLf & _
            "Setelah mencoba memasukkan nilai tak-valid: " & vbCrLf & _
            "Waktu universal: " & waktu.KeStringUniversal() & _
            vbCrLf & "Waktu standar: " & waktu.KeStringStandar()

        MessageBox.Show(keluaran, "Menguji Kelas CWaktu")
    End Sub ' Main

End Module ' modUjiWaktu



Gambar 7.3 Keluaran program pada kode 7.2


Baris 17 menetapkan waktu dari objek CWaktu dengan melewatkan argumen waktu yang valid kepada metode SetWaktu. Baris 19-23 menempatkan waktu pada keluaran dalam kedua format universal dan format standar untuk memastikan bahwa waktu telah ditetapkan secara benar.

Untuk mengilustrasikan bagaimana metode SetWaktu memvalidasi nilai-nilai yang dilewatkan kepadanya, baris 25 melewatkan argumen waktu tak-valid kepada SetWaktu. Baris 27-30 menampilkan waktu keluaran dalam kedua format, dan baris 32 menampilkan sebuah MessageBox dengan hasil keluaran program. Perhatikan pada dua baris terakhir bahwa waktu ditetapkan menjadi tengah malam, yang merupakan nilai default bagi objek CWaktu.

CWaktu merupakan contoh pertama yang tidak mendefinisikan metode Main, sehingga ia tak bisa dieksekusi. Module (modUjiWaktu), meskipun secara teknis bukan sebuah kelas, berperan sebagai kelas aplikasi yang mendefinisikan metode Main, yang merupakan titik entri untuk sebuah program dalam Visual Basic. Kelas CWaktu tidak mendefinisikan Main dan tidak bisa dijadikan titik entri pada program.

Perhatikan bahwa program mendeklarasikan variabel instans mJam, mMenit, dan mDetik sebagai Private. Variabel instans yang dideklarasikan Private tidak dapat diakses dari luar kelasnya.

Pada program ini, konstruktor CWaktu menginisialisasi semua variabel instans dengan 0. Variabel instans dari sebuah objek CWaktu tidak dapat menyimpan nilai tak-valid, karena konstruktor (yang memanggil SetWaktu) dipanggil ketika objek CWaktu diciptakan. Metode SetWaktu memeriksa pemodifikasian atas variabel instans oleh klien.

Normalnya, variabel instans diinisialisasi di dalam konstruktor kelas, tetapi dapat pula diinisialisasi ketika dideklarasikan di dalam tubuh kelas. Jika programer tidak menginisialisasi variabel instans secara eksplisit, kompiler akan menginisialisasinya. Ketika hal ini terjadi, kompiler akan menetapkan semua variabel numerik primitif menjadi 0, Boolean menjadi False, referensi menjadi Nothing.


Skop Kelas
Skop metode telah didiskusikan, dan sekarang saatnya untuk mendiskusikan skop kelas. Variabel dan metode instans memiliki skop kelas. Di dalam skop kelas, semua anggota kelas dapat diakses oleh setiap metode kelas terkait dan dapat direferensi dengan nama. Di luar skop kelas, anggota kelas tidak dapat direferesi dengan secara langsung. Jika sebuah variabel didefinisikan di dalam suatu metode, maka hanya metode tersebut yang dapat mengakses variabel itu (yaitu, variabel itu merupakan variabel lokal di dalam metode). Variabel semacam itu memiliki skop blok. Jika sebuah metode mendefinisikan suatu variabel yang memiliki nama sama dengan variabel dengan skop kelas, maka variabel skop blok menyembunyikan variabel skop kelas di dalam skop metode. Variabel instans yang tersembunyi dapat diakses di dalam sebuah metode menggunakan katakunci Me dan operator dot, seperti Me.mJam. Katakunci Me akan didiskusikan nanti pada bab ini.


Pengendalian Akses terhadap Anggota Kelas
Pemodifikasi akses anggota Public dan Private mengendalikan akses terhadap metode dan variabel instans. (Pada Bab 8, akan dikenalkan pemodifikasi akses yang lain, Protected dan Friend).

Aplikasi pada kode 7.3 mendemonstrasikan bahwa anggota-anggota kelas Private tidak dapat diakses dari luar kelas. Baris 9 mencoba untuk mengakses variabel instans Private, mJam, dari objek CWaktu (waktu). Kompiler membangkitkan error yang menyatakan bahwa anggota Private, mJam, tidak dapat diakses. (Perhatikan: program ini mengasumsikan bahwa kelas CWaktu pada kode 7.1 digunakan).

1
2
3
4
5
6
7
8
9
10
11
12
' Kode 7.3: AksesDibatasi.vb
' Demonstrasi error akibat pengaksesan anggota kelas Private.

Module modAksesDibatasi

    Sub Main()
        Dim waktu As New CWaktu()

        waktu.mJam = 7 ' error
    End Sub ' Main

End Module ' modAksesDibatasi




Gambar 7.4 Keluaran program pada kode 7.3


Akses terhadap data Private harus dikendalikan secara hati-hati oleh semua metode suatu kelas. Untuk mengijinkan klien membaca nilai dari data Private, kelas dapat menyediakan suatu definisi properti, yang memampukan pengguna untuk mengakses data Private secara aman. Properti, yang nanti akan didiskusikan, memuat aksesor, atau potongan kode yang menangani detil pemodifikasian dan pengembalian nilai balik. Definisi properti dapat memuat aksesor Get, aksesor Set, atau keduanya. Aksesor Get memampukan klien untuk membaca nilai data Private, sedangkan aksesor Set memampukan klien untuk memodifikasi nilai data Private. Pemodifikasian semacam itu sepertinya melanggar makna privasi dari data Private. Namun, aksesor Set dapat menyediakan kapabilitas validasi-data (seperti pemeriksaan rentang) untuk memastikan bahwa nilai ditetapkan secara benar. Aksesor Set juga dapat menerjemahkan antara format yang digunakan di dalam antarmuka dan format yang digunakan di dalam implementasi.


Penginisialisasian Objek Kelas: Konstruktor
Sebuah metode konstruktor menginisialisasi semua anggota kelas. Programer menuliskan kode untuk konstruktor, yang akan dipanggil setiap kali sebuah objek dari kelas tersebut diinstansiasi. Variabel instans dapat diinisialisasi secara implisit dengan nilai default (0 untuk tipe numerik primitif, False untuk Boolean, dan Nothing untuk referensi). Visual Basic menginisialisasi variabel dengan nilai defaultnya ketika dideklarasikan pada saat program dieksekusi. Variabel dapat diinisialisasi ketika dideklarasikan di dalam tubuh kelas atau di dalam konstruktor. Meskipun variabel instans diinisialisasi di dalam konstruktor, variabel tersebut diinisialisasi (dengan nilai defaultnya) pada saat program dieksekusi sebelum sembarang konstruktor dipanggil. Kelas dapat memuat konstruktor teroverload untuk menyediakan pelbagai cara dalam menginisialisasi objek kelas.

Ketika menciptakan objek suatu kelas, programer dapat menyediakan penginisialisasi yang diapit sepasang kurung di sebelah kanan nama kelas. Penginisialiasi ini adalah argumen bagi konstruktor kelas. Secara umum, deklarasi ini mempunyai format

Dim referensiObjek As New NamaKelas( argumen-argumen )

dimana referensiObjek merupakan sebuah referensi dari tipe data tertentu, New mengindikasikan bahwa objek sedang diciptakan, NamaKelas mengindikasikan tipe dari objek baru, dan argumen-argumen menspesifikasi nilai-nilai yang digunakan konstruktor kelas untuk menginisialisasi objek. Sebuah konstruktor yang memuat argumen acapkali dikenal dengan konstruktor terparameterisasi. Contoh berikutnya (kode 7.4) akan mendemonstrasikan kegunaan penginisialisasi ini.

Jika sebuah kelas tidak mendefinisikan sembarang konstruktor, kompiler akan menyediakan suatu konstruktor default. Konstruktor ini tidak memuat kode apapun (konstruktor kosong) dan tidak mempunyai argumen. Programer dapat pula menyediakan konstruktor default, seperti yang didemonstrasikan pada kelas CWaktu (kode 7.1).


Menggunakan Konstruktor Teroverload
Seperti metode, konstruktor suatu kelas dapat dioverload. Ini berarti bahwa beberapa konstruktor di dalam suatu kelas dapat menyediakan nama metode yang sama (yaitu, New). Untuk mengoverload konstruktor, definisi metode yang terpisah dengan nama sama disediakan untuk tiap versi metode. Ingat bahwa konstruktor teroverload harus memiliki jumlah dan/atau tipe dan/atau urutan parameter.

Konstruktor CWaktu pada kode 7.1 menginisialisasi mJam, mMenit, dan mDetik dengan 0 (pukul 12 dalam waktu universal) dengan sebuah pemanggilan terhadap metode SetWaktu. Kelas CWaktu2 (kode 7.4) mengoverload metode konstruktor untuk menyediakan beberapa cara dalam menginisialisasi objek CWaktu2. Setiap konstruktor memanggil metode SetWaktu dari objek CWaktu2, yang memastikan semua nilai yang berada di luar rentang ditetapkan menjadi nol. Visual Basic memanggil konstruktor yang sesuai dengan mencocokkan jumlah, tipe, dan urutan argumen yang dispesifikasi di dalam pemanggilan konstruktor dengan jumlah, tipe, dan urutan parameter yang dispesifikasi di dalam setiap definisi metode konstruktor.

Karena kebanyakan kode pada kelas CWaktu2 identik dengan yang ada pada kelas CWaktu, bagian ini hanya akan dikonsentrasikan pada konstruktor teroverload. Baris 14 mendefinisikan konstruktor default. Baris 20 mendefinisikan sebuah konstruktor CWaktu2 yang menerima sebuah argumen Integer, yang merepresentasikan mJam. Baris 26 mendefinisikan sebuah konstruktor CWaktu2 yang menerima dua argumen Integer, yang merepresentasikan mJam dan mMenit. Baris 33 mendefinisikan sebuah konstruktor CWaktu2 yang menerima tiga argumen Integer, yang merepresentasikan mJam, mMenit, dan mDetik.

Baris 40 mendefinisikan sebuah konstruktor CWaktu2 yang menerima sebuah referensi yang menunjuk ke objek CWaktu2 yang lain. Ketika konstruktor terakhir ini dipakai, semua nilai dari argumen CWaktu2 dipakai untuk menginisialisasi mJam, mMenit, dan mDetik. Meskipun kelas CWaktu2 mendeklarasikan ketiga nilai tersebut sebagai Private (baris 8-10), objek CWaktu2 dapat mengakses nilainya secara langsung menggunakan ekspresi nilaiWaktu.mJam, nilaiWaktu.mMenit, dan nilaiWaktu.mDetik.

Konstruktor tidak bisa memiliki nilai balik, karena akan menyebabkan error sintaks. Di samping itu, perhatikan bahwa setiap konstruktor meneriman jumlah berbeda atau tipe berbeda dari argumen. Meskipun hanya dua konstruktor menerima nilai-nilai untuk mJam, mMenit, dan mDetik, setiap konstruktor memanggil SetWaktu dengan nilai-nilai untuk mJam, mMenit, dan mDetik dan menetapkan nilai nol untuk setiap nilai yang absen.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
' Kode 7.4: CWaktu2.vb
' Merepresentasikan waktu dan memuat beberapa konstruktor teroverload

Public Class CWaktu2
    Inherits Object

    ' mendeklarasikan nilai instans Integer untuk jam, menit, dan detik
    Private mJam As Integer ' 0 - 23
    Private mMenit As Integer ' 0 - 59
    Private mDetik As Integer ' 0 - 59

    ' Metode New adalah metode konstruktur CWaktu2, yang menginisialisasi
    ' variabel instans dengan nol
    Public Sub New()
        SetWaktu()
    End Sub ' New

    ' konstruktor CWaktu2: jam disediakan;
    ' menit dan detik didefault menjadi 0
    Public Sub New(ByVal nilaiJam As Integer)
        SetWaktu(nilaiJam)
    End Sub ' New

    ' konstruktor CWaktu2: jam dan menit disediakan;
    ' detik didefault menjadi 0
    Public Sub New(ByVal nilaiJam As Integer, _
        ByVal nilaiMenit As Integer)

        SetWaktu(nilaiJam, nilaiMenit)
    End Sub ' New

    ' konstruktor CWaktu2: jam, menit, dan detik disediakan
    Public Sub New(ByVal nilaiJam As Integer, _
        ByVal nilaiMenit As Integer, ByVal nilaiDetik As Integer)

        SetWaktu(nilaiJam, nilaiMenit, nilaiDetik)
    End Sub ' New

    ' konstruktor CWaktu2: objek CWaktu2 lain disediakan
    Public Sub New(ByVal nilaiWaktu As CWaktu2)
        SetWaktu(nilaiWaktu.mJam, nilaiWaktu.mMenit, nilaiWaktu.mDetik)
    End Sub ' New

    ' menetapkan nilai waktu baru menggunakan waktu universal;
    ' melakukan pemeriksaan validitas pada data;
    ' menetapkan nilai tak-valid menjadi nol
    Public Sub SetWaktu(Optional ByVal nilaiJam As Integer = 0, _
        Optional ByVal nilaiMenit As Integer = 0, _
        Optional ByVal nilaiDetik As Integer = 0)

        ' memeriksa jika jam berada di antara 0 dan 23, maka jam ditetapkan
        If (nilaiJam >= 0 AndAlso nilaiJam < 24) Then
            mJam = nilaiJam
        Else
            mJam = 0
        End If

        ' memeriksa jika menit berada di antara 0 dan 59, maka menit ditetapkan
        If (nilaiMenit >= 0 AndAlso nilaiMenit < 60) Then
            mMenit = nilaiMenit
        Else
            mMenit = 0
        End If

        ' memeriksa jika detik berada di antara 0 dan 59, maka detik ditetapkan
        If (nilaiDetik >= 0 AndAlso nilaiDetik < 60) Then
            mDetik = nilaiDetik
        Else
            mDetik = 0
        End If

    End Sub ' SetWaktu

    ' mengkonversi String menjadi format waktu-universal
    Public Function KeStringUniversal() As String
        Return String.Format("{0}:{1:D2}:{2:D2}", _
        mJam, mMenit, mDetik)
    End Function ' KeStringUniversal

    ' mengkonversi String dalam format-standar
    Public Function KeStringStandar() As String
        Dim sufiks As String = " SORE"
        Dim format As String = "{0}:{1:D2}:{2:D2}"
        Dim jamStandar As Integer

        ' menentukan waktu apakah PAGI atau SORE
        If mJam < 12 Then
            sufiks = " PAGI"
        End If

        ' mengkonversi dari format waktu-universal menjadi format waktu-standar
        If (mJam = 12 OrElse mJam = 0) Then
            jamStandar = 12
        Else
            jamStandar = mJam Mod 12
        End If

        Return String.Format(format, jamStandar, mMenit, _
            mDetik) & sufiks
    End Function ' KeStringStandar

End Class  ' CWaktu2


Kode 7.5 (modUjiWaktu2) mendemonstrasikan kegunaan beberapa konstruktor teroverload (kode 7.4). Baris 11-16 menciptakan enam objek CWaktu2 yang memanggil berbagai konstruktor kelas. Baris 11 menspesifikasi bahwa ia memanggil konstruktor default dengan menempatkan kurung kosong setelah nama kelas. Baris 12-16 mendemonstrasikan pelewatan argumen kepada konstruktor CWaktu2. Untuk memanggil konstruktor yang sesuai, dilewatkan jumlah, tipe, dan urutan argumen yang sesuai (dispesifikasi oleh definisi konstruktor) kepada konstruktor tersebut. Sebagai contoh, baris 13 memanggil konstruktor yang didefinisikan pada baris 26-30 pada kode 7.4. Baris 21-55 memanggil metode KeStringUniversal dan KeStringStandar untuk tiap objek CWaktu2 untuk mendemonstrasikan bagaimana konstruktor menginisialisasi objek.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
' Kode 7.5: UjiWaktu2.vb
' Demonstrasi pengoverloadan konstruktor.

Imports System.Windows.Forms

Module modUjiWaktu2

    Sub Main()

        ' menggunakan konstruktor-konstruktor teroverload
        Dim waktu1 As New CWaktu2()
        Dim waktu2 As New CWaktu2(2)
        Dim waktu3 As New CWaktu2(21, 34)
        Dim waktu4 As New CWaktu2(12, 25, 42)
        Dim waktu5 As New CWaktu2(27, 74, 99)
        Dim waktu6 As New CWaktu2(waktu4) ' menggunakan waktu2 sebagai nilai awal

        Const SPASI As Integer = 13 ' spasi di antara keluaran

        ' memanggil metode-metode waktu1
        Dim keluaran As String = "Dikonstruksi dengan: " & vbCrLf & _
        " waktu1: semua argumen didefault" & vbCrLf & _
        Space(SPASI) & waktu1.KeStringUniversal() & _
        vbCrLf & Space(SPASI) & waktu1.KeStringStandar()

        ' memanggil metode-metode waktu2
        keluaran &= vbCrLf & _
        " waktu2: jam disediakan; menit dan jam didefault" & _
        vbCrLf & Space(SPASI) & _
        waktu2.KeStringUniversal() & vbCrLf & Space(SPASI) & _
        waktu2.KeStringStandar()

        ' memanggil metode-metode waktu3
        keluaran &= vbCrLf & _
        " waktu3: jam dan menit disediakan; detik didefault" & _
        vbCrLf & Space(SPASI) & waktu3.KeStringUniversal() & _
        vbCrLf & Space(SPASI) & waktu3.KeStringStandar()

        ' memanggil metode-metode waktu4
        keluaran &= vbCrLf & _
        " waktu4: jam, menit, dan detik disediakan" & _
        vbCrLf & Space(SPASI) & waktu4.KeStringUniversal() & _
        vbCrLf & Space(SPASI) & waktu4.KeStringStandar()

        ' memanggil metode-metode waktu5
        keluaran &= vbCrLf & _
        " waktu5: jam, menit, dan detik disediakan" & _
        vbCrLf & Space(SPASI) & waktu5.KeStringUniversal() & _
        vbCrLf & Space(SPASI) & waktu5.KeStringStandar()

        ' memanggil metode-metode waktu6
        keluaran &= vbCrLf & _
        " waktu6: objek CWaktu2 waktu4 disediakan" & vbCrLf & _
        Space(SPASI) & waktu6.KeStringUniversal() & _
        vbCrLf & Space(SPASI) & waktu6.KeStringStandar()

        MessageBox.Show(keluaran, _
        "Mendemonstrasikan Konstruktor Teroverload")
    End Sub ' Main

End Module ' modUjiWaktu2



Gambar 7.5 Keluaran program pada kode 7.5


Setiap konstruktor CWaktu2 dapat ditulis untuk menyertakan salinan beberapa statemen tertentu dari metode SetWaktu. Ini sedikit lebih efisien, karena mengeliminasi pemanggilan ekstra terhadap SetWaktu. Namun, perhatikan apa yang akan terjadi jika programer mengubah representasi waktu dari tiga nilai Integer (yang memerlukan 12 byte memori) menjadi sebuah nilai Integer yang merepresentasikan jumlah detik total (yang memerlukan 4 byte memori). Penempatan kode yang identik di dalam konstruktor CWaktu2 dan metode SetWaktu membuat perubahan semacam itu di dalam definisi kelas menjadi lebih sulit. Jika implementasi dari metode SetWaktu berubah, maka implementasi dari konstruktor CWaktu2 juga perlu diubah. Jika konstruktor CWaktu2 memanggil SetWaktu secara langsung, maka perubahan pada implementasi SetWaktu dilakukan hanya sekali, sehingga mereduksi kemungkinan error pemrograman.


Properti
Metode suatu kelas dapat memanipulasi variabel instans Private dari kelas tersebut. Manipulasi bisa berupa perubahan terhadap saldo akun, sebuah variabel instans Private dari kelas CAkunBank, yang dilakukan oleh metode HitungBunga.

Kelas seringkali menyediakan beberapa properti Public untuk mengijinkan klien dalam menetapkan (menugaskan nilai kepada) atau mendapatkan (memperoleh nilai dari) variabel instans Private. Kode 7.6 menunjukkan bagaimana menciptakan tiga properti, Jam, Menit, dan Detik. Jam dipakai untuk mengakses mJam, Menit mengakses variabel mMenit, dan Detik mengakses variabel mDetik. Setiap properti memiliki aksesor Get (untuk mendapatkan nilai bidang) dan aksesor Set (untuk memodifikasi nilai bidang).

Meskipun penyediaan aksesor Set dan Get tampak seperti pembuatan variabel instans menjadi Public, tetapi hal ini bukanlah seperti itu. Ini merupakan salah satu fitur di dalam Visual Basic yang membuat bahasa ini atraktif dari sudut pandang rekasaya perangkat-lunak. Jika sebuah variabel instans adalah Public, maka variabel itu dapat dibaca atau ditulis oleh sembarang metode di dalam program. Jika sebuah variabel instans adalah Private, maka metode get Public seolah-olah mengijinkan metode lain membaca data sesuka hati. Namun, metode get dapat mengendalikan pemformatan dan penampilan data. Metode set Public dapat menguji setiap percobaan dalam memodifikasi nilai variabel instans, sehingga memastikan bahwa nilai baru cocok untuk anggota data tersebut. Sebagai contoh, setiap percobaan untuk menetapkan nilai hari dalam bulan menjadi 37 akan ditolak, dan setiap percobaan untuk menetapkan berat seseorang menjadi negatif akan ditolak. Oleh karena itu, meskipun metode set dan get menyediakan akses terhadap data Private, implementasi dari metode tersebut dapat membatasi akses terhadap data Private.

Kode 7.6 memperbaiki kelas CWaktu (sekarang disebut dengan CWaktu3) dengan menyertakan beberapa properti untuk variabel instan Private, mJam, mMenit, dan mDetik. Aksesor Set mengendalikan penetapan variabel instans agar menjadi nilai valid. Setiap percobaan untuk menetapkan sembarang variabel instans menjadi nilai tak-valid menyebabkan variabel instans tersebut menjadi nol. Aksesor Get menghasilkan nilai balik berupa nilai dari variabel instans tertentu.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
' Kode 7.6: CWaktu3.vb
' Merepresentasikan waktu dan memuat beberapa properti

Public Class CWaktu3
    Inherits Object

    ' mendeklarasikan nilai instans Integer untuk jam, menit, dan detik
    Private mJam As Integer ' 0 - 23
    Private mMenit As Integer ' 0 - 59
    Private mDetik As Integer ' 0 - 59

    ' Metode New adalah metode konstruktur CWaktu3, yang menginisialisasi
    ' variabel instans dengan nol
    Public Sub New()
        SetWaktu(0, 0, 0)
    End Sub ' New

    ' konstruktor CWaktu3: jam disediakan;
    ' menit dan detik didefault menjadi 0
    Public Sub New(ByVal nilaiJam As Integer)
        SetWaktu(nilaiJam, 0, 0)
    End Sub ' New

    ' konstruktor CWaktu3: jam dan menit disediakan;
    ' detik didefault menjadi 0
    Public Sub New(ByVal nilaiJam As Integer, _
        ByVal nilaiMenit As Integer)

        SetWaktu(nilaiJam, nilaiMenit, 0)
    End Sub ' New

    ' konstruktor CWaktu3: jam, menit, dan detik disediakan
    Public Sub New(ByVal nilaiJam As Integer, _
        ByVal nilaiMenit As Integer, ByVal nilaiDetik As Integer)

        SetWaktu(nilaiJam, nilaiMenit, nilaiDetik)
    End Sub ' New

    ' konstruktor CWaktu3: objek CWaktu3 lain disediakan
    Public Sub New(ByVal nilaiWaktu As CWaktu3)
        SetWaktu(nilaiWaktu.mJam, nilaiWaktu.mMenit, _
            nilaiWaktu.mDetik)
    End Sub ' New

    ' menetapkan nilai waktu baru menggunakan waktu universal;
    ' menggunakan properti untuk memeriksa validitas pada data
    Public Sub SetWaktu(ByVal nilaiJam As Integer, _
        ByVal nilaiMenit As Integer, ByVal nilaiDetik As Integer)

        Jam = nilaiJam ' kelihatan
        Menit = nilaiMenit ' berbahaya
        Detik = nilaiDetik ' tetapi benar
    End Sub ' SetWaktu

    ' properti Jam
    Public Property Jam() As Integer

        ' menghasilkan nilai mJam
        Get
            Return mJam
        End Get

        ' menetapkan nilai mJam
        Set(ByVal nilai As Integer)

            If (nilai >= 0 AndAlso nilai < 24) Then
                mJam = nilai
            Else
                mJam = 0
            End If

        End Set

    End Property ' Jam

    ' properti Menit
    Public Property Menit() As Integer

        ' menghasilkan nilai mMenit
        Get
            Return mMenit
        End Get

        ' menetapkan nilai mMenit
        Set(ByVal nilai As Integer)

            If (nilai >= 0 AndAlso nilai < 60) Then
                mMenit = nilai
            Else
                mMenit = 0
            End If

        End Set

    End Property ' Menit

    ' properti Detik
    Public Property Detik() As Integer

        ' menghasilkan nilai mDetik
        Get
            Return mDetik
        End Get

        ' menetapkan nilai mDetik
        Set(ByVal nilai As Integer)

            If (nilai >= 0 AndAlso nilai < 60) Then
                mDetik = nilai
            Else
                mDetik = 0
            End If

        End Set

    End Property ' Detik

    ' mengkonversi String menjadi format waktu-universal
    Public Function KeStringUniversal() As String
        Return String.Format("{0}:{1:D2}:{2:D2}", _
            mJam, mMenit, mDetik)
    End Function ' KeStringUniversal

    ' mengkonversi String dalam format-standar
    Public Function KeStringStandar() As String
        Dim sufiks As String = " SORE"
        Dim format As String = "{0}:{1:D2}:{2:D2}"
        Dim jamStandar As Integer

        ' menentukan waktu apakah PAGI atau SORE
        If mJam < 12 Then
            sufiks = " PAGI"
        End If

        ' mengkonversi dari format waktu-universal menjadi format waktu-standar
        If (mJam = 12 OrElse mJam = 0) Then
            jamStandar = 12
        Else
            jamStandar = mJam Mod 12
        End If

        Return String.Format(format, jamStandar, mMenit, _
            mDetik) & sufiks
    End Function ' KeStringStandar

End Class  ' CWaktu3

Baris 56-74, 77-95, dan 98-116 mendefinisikan properti Jam, Menit, dan Detik pada kelas CWaktu3. Setiap properti diawali dengan baris deklarasi, yang menyertakan pemodifikasi akses (Public), nama properti (Jam, Menit, atau Detik), dan tipe properti (Integer).

Tubuh properti memuat aksesor Get dan Set, yang dideklarasikan menggunakan katakunci Get dan Set. Deklarasi metode aksesor Get berada pada baris 59-61, 80-82, dan 101-103. Setiap metode Get menghasilkan nilai balik berupa variabel instans mJam, mMenit, dan mDetik. Aksesor Set dideklarasikan pada baris 64-72, 85-93, dan 106-114. Tubuh setiap aksesor Set melakukan statemen kondisional yang sebelumnya berada di dalam metode SetWaktu.

Metode SetWaktu (baris 47-53) sekarang menggunakan properti Jam, Menit, dan Detik untuk memastikan bahwa variabel instans mJam, mMenit, dan mDetik memiliki nilai yang valid. Setelah sebuah properti didefinisikan, Anda bisa menggunakannya dengan cara yang sama seperti menggunakan sebuah variabel. Anda menugaskan nilai kepada properti menggunakan operator penugasan (=). Ketika penugasan ini terjadi, kode di dalam definisi aksesor Set untuk properti tersebut akan dieksekusi. Pereferensian properti (misalnya, menggunakannya di dalam perhitungan matematik) akan mengeksekusi kode di dalam definisi aksesor Get untuk properti itu.

Kode 7.7 (kelas FrmUjiWaktu3), yang merepresentasikan GUI untuk kelas CWaktu3 (baris 30 merepresentasikan kode yang dibangkitkan oleh Visual Studio), mendeklarasikan dan menginstansiasi objek dari kelas CWaktu3 (baris 28). GUI memuat tiga bidang teks dimana di dalamnya pengguna dapat memasukkan nilai untuk variabel mJam, mMenit, dan mDetik. Baris 68-92 mendeklarasikan tiga metode yang menggunakan properti Jam, Menit, dan Detik dari kelas CWaktu3 untuk mengubah nilai-nilai terkait. GUI juga memuat sebuah tombol yang memampukan pengguna dalam menginkremen mDetik sebesar 1 tanpa perlu menggunakan kotak teks. Dengan menggunakan properti, metode cmdTambahDetik_Click (baris 43-65) dapat menentukan dan menetapkan waktu baru. Sebagai contoh, 23:59:59 menjadi 00:00:00 ketika pengguna menekan tombol.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
' Gambar 7.7: UjiWaktu3.vb
' Demonstrasi beberapa properti.

Imports System.Windows.Forms

Public Class FrmUjiWaktu3
    Inherits Form

    ' Label dan TextBox untuk jam
    Friend WithEvents lblSetJam As Label
    Friend WithEvents txtSetJam As TextBox

    ' Label dan TextBox untuk menit
    Friend WithEvents lblSetMenit As Label
    Friend WithEvents txtSetMenit As TextBox

    ' Label dan TextBox untuk detik
    Friend WithEvents lblSetDetik As Label
    Friend WithEvents txtSetDetik As TextBox

    ' Label untuk menampilkan waktu
    Friend WithEvents lblKeluaran1 As Label
    Friend WithEvents lblKeluaran2 As Label

    ' Tombol untuk menambahkan satu detik pada waktu
    Friend WithEvents cmdTambahDetik As Button

    Dim waktu As New CWaktu3()

    ' kode yang dibangkitkan oleh Visual Studio .NET

    ' memperbarui waktu
    Private Sub TampilPerbarui()
        lblKeluaran1.Text = "Jam: " & waktu.Jam & "; Menit: " & _
        waktu.Menit & "; Detik: " & waktu.Detik

        lblKeluaran2.Text = "Waktu standar adalah: " & _
        waktu.KeStringStandar & "; Waktu universal adalah: " _
        & waktu.KeStringUniversal()
    End Sub ' TampilPerbarui

    ' dipanggil ketika pengguna menekan tombol Tambah 1 Detik
    Private Sub cmdTambahDetik_Click(ByVal _
        sender As System.Object, _
        ByVal e As System.EventArgs) Handles cmdTambahDetik.Click

        ' menambah satu detik
        waktu.Detik = (waktu.Detik + 1) Mod 60
        txtSetDetik.Text = waktu.Detik

        ' menambah satu menit jika 60 detik terlewati
        If waktu.Detik = 0 Then
            waktu.Menit = (waktu.Menit + 1) Mod 60
            txtSetMenit.Text = waktu.Menit

            ' menambah satu jam jika 60 menit terlewati
            If waktu.Menit = 0 Then
                waktu.Jam = (waktu.Jam + 1) Mod 24
                txtSetJam.Text = waktu.Jam
            End If

        End If

        TampilPerbarui()
    End Sub ' cmdTambahDetik_Click

    ' menangani event ketika teks pada txtSetJam berubah
    Private Sub txtSetJam_TextChanged(ByVal sender As  _
        System.Object, ByVal e As System.EventArgs) _
        Handles txtSetJam.TextChanged

        waktu.Jam = Convert.ToInt32(txtSetJam.Text)
        TampilPerbarui()
    End Sub  ' txtSetJam_TextChanged

    ' menangani event ketika teks pada txtSetMenit berubah
    Private Sub txtSetMenit_TextChanged(ByVal sender As  _
        System.Object, ByVal e As System.EventArgs) _
        Handles txtSetMenit.TextChanged

        waktu.Menit = Convert.ToInt32(txtSetMenit.Text)
        TampilPerbarui()
    End Sub  ' txtSetMenit_TextChanged

    ' menangani event ketika teks pada txtSetDetik berubah
    Private Sub txtSetDetik_TextChanged(ByVal sender _
        As System.Object, ByVal e As System.EventArgs) _
        Handles txtSetDetik.TextChanged

        waktu.Detik = Convert.ToInt32(txtSetDetik.Text)
        TampilPerbarui()
    End Sub  ' txtSetDetik_TextChanged

End Class  ' FrmUjiWaktu3





Gambar 7.6 GUI untuk kelas CWaktu3


Tidak semua properti harus memiliki aksesor Get dan Set. Sebuah properti dengan hanya aksesor Get dikenal dengan properti read-only dan harus dideklarasikan menggunakan katakunci ReadOnly. Sebaliknya, sebuah properti dengan hanya aksesor Set dikenal dengan properti write-only dan harus dideklarasikan menggunakan katakunci WriteOnly. Secara umum, properti WriteOnly jarang digunakan.

Komposisi: Objek sebagai Variabel Instans dari Kelas Lain
Dalam banyak situasi, pereferensian objek yang telah ada lebih efisien dilakukan daripada menulis-ulang kode objek untuk kelas baru di dalam projek baru. Dimisalkan bahwa Anda akan mengimplementasikan sebuah objek kelas CJamAlarm yang perlu mengetahui kapan harus membunyikan alarm. Akan lebih mudah untuk mereferensi objek CWaktu yang telah ada daripada harus menulis objek CWaktu yang baru. Kegunaan referensi yang menunjuk kepada objek dari kelas sudah ada dikenal dengan komposisi.

Aplikasi pada kode 7.8, kode 7.9 dan kode 7.10 mendemonstrasikan komposisi. Kelas CHari (kode 7.8) mengenkapsulasi informasi yang berkaitan dengan tanggal tertentu. Baris 9-11 mendeklarasikan tiga Integer, mBulan, mHari, dan mTahun. Baris 15-35 mendefinisikan konstruktor, yang menerima nilai-nilai untuk mBulan, mHari, dan mTahun sebagai argumen, kemudian menugaskannya kepada variabel-variabel kelas setelah memastikan bahwa semua variabel tersebut memiliki nilai yang valid.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
' Kode 7.8: CHari.vb
' Enkapsulasi bulan, hari, dan tahun.

Imports System.Windows.Forms

Class CHari
    Inherits Object

    Private mBulan As Integer ' 1-12
    Private mHari As Integer ' 1-31 tergantung bulan
    Private mTahun As Integer ' sembarang year

    ' konstruktor menegaskan nilai sesuai untuk bulan, kemudian memanggil
    ' metode PeriksaHari untuk memastikan nilai sesuai untuk hari
    Public Sub New(ByVal nilaiBulan As Integer, _
        ByVal nilaiHari As Integer, ByVal nilaiTahun As Integer)

        ' memastikan nilai bulan valid
        If (nilaiBulan > 0 AndAlso nilaiBulan <= 12) Then
            mBulan = nilaiBulan
        Else
            mBulan = 1

            ' informasikan pengguna tentang error
            Dim pesanError As String = _
                "Bulan tak-valid. Tetapkan bulan menjadi 1."

            MessageBox.Show(pesanError, "", _
                MessageBoxButtons.OK, MessageBoxIcon.Error)
        End If

        mTahun = nilaiTahun
        mHari = PeriksaHari(nilaiHari) ' memvalidasi hari

    End Sub ' New

    ' menegaskan hari sesuai berdasarkan bulan dan tahun
    Private Function PeriksaHari(ByVal ujiNilaiHari As Integer) _
        As Integer

        Dim hariPerBulan() As Integer = _
            {0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31}

        If (ujiNilaiHari > 0 AndAlso _
            ujiNilaiHari <= hariPerBulan(mBulan)) Then

            Return ujiNilaiHari
        End If

        ' memeriksa tahun leap pada Pebruari
        If (mBulan = 2 AndAlso ujiNilaiHari = 29 AndAlso _
            mTahun Mod 400 = 0 OrElse mTahun Mod 4 = 0 AndAlso _
            mTahun Mod 100 <> 0) Then

            Return ujiNilaiHari
        Else

            ' informasikan pengguna tentang error
            Dim pesanError As String = _
                "hari " & ujiNilaiHari & "tak-valid. Tetapkan hari menjadi 1. "

            MessageBox.Show(pesanError, "", _
                MessageBoxButtons.OK, MessageBoxIcon.Error)

            Return 1 ' agar tetap valid
        End If

    End Function ' PeriksaHari

    ' menciptakan string yang memuat format bulan/hari/tahun
    Public Function KeStringStandar() As String
        Return mBulan & "/" & mHari & "/" & mTahun
    End Function ' KeStringStandar

End Class ' CHari

Kelas CKaryawan (kode 7.9) memuat informasi yang berkaitan dengan tanggal lahir dan tanggal mulai kerja seorang karyawan (baris 7-10) menggunakan variabel instans mNamaPertama, mNamaAkhir, mTanggalUltah, dan mTanggalKerja. Anggota mTanggalUltah dan mTanggalKerja adalah referensi yang menunjuk ke objek CHari, masing-masing memuat variabel instans mBulan, mHari, dan mTahun. Pada contoh ini, kelas CKaryawan dikomposisi dari dua referensi kelas CHari. Konstruktor CKaryawan (baris 13-32) mengambil delapan argumen (nilaiNamaPertama, nilaiNamaAkhir, nilaiBulanLahir, nilaiHariLahir, nilaiTahunLahir, nilaiBulanKerja, nilaiHariKerja, dan nilaiTahunKerja. Baris 26-27 melewatkan argumen nilaiBulanLahir, nilaiHariLahir, dan nilaiTahunLahir kepada konstruktor CHari untuk menciptakan objek mHariUltah. Sama halnya, baris 30-31 melewatkan argumen nilaiBulanKerja, nilaHariKerja, dan nilaiTahunKerja kepada konstruktor CHari untuk menciptakan objek mAwalKerja.

Module modUjiKomposisi (kode 7.10) menjalankan aplikasi dengan metode Main. Baris 9-10 menginstansiasi sebuah objek CKaryawan (“Djumanggal Sianipar” dengan hari ulang tahun 3/21/1950 dan tanggal mulai kerja 3/12/1975), dan baris 12-13 menampilkan informasi kepada pengguna di dalam sebuah MessageBox.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
' Kode 7.9: CKaryawan.vb
' Representasi nama, tanggal lahir, dan tanggal mulai kerja karyawan.

Class CKaryawan
    Inherits Object

    Private mNamaPertama As String
    Private mNamaAkhir As String
    Private mTanggalUltah As CHari ' referensi objek anggota
    Private mTanggalKerja As CHari ' referensi objek anggota

    ' konstruktor CKaryawan
    Public Sub New(ByVal nilaiNamaPertama As String, _
        ByVal nilaiNamaAkhir As String, _
        ByVal nilaiBulanLahir As Integer, _
        ByVal nilaiHariLahir As Integer, _
        ByVal nilaiTahunLahir As Integer, _
        ByVal nilaiBulanKerja As Integer, _
        ByVal nilaiHariKerja As Integer, _
        ByVal nilaiTahunKerja As Integer)

        mNamaPertama = nilaiNamaPertama
        mNamaAkhir = nilaiNamaAkhir

        ' menciptakan instans CHari untuk ultah karyawan
        mTanggalUltah = New CHari(nilaiBulanLahir, nilaiHariLahir, _
            nilaiTahunLahir)

        ' mencipakan instans CHari untuk tanggal kerja karyawan
        mTanggalKerja = New CHari(nilaiBulanKerja, nilaiHariKerja, _
            nilaiTahunKerja)
    End Sub ' New

    ' menghasilkan informasi karyawan sebagai String format standar
    Public Function KeStringStandar() As String
        Return mNamaAkhir & ", " & mNamaPertama & " Dipekerjakan: " _
        & mTanggalKerja.KeStringStandar() & " Tanggal Lahir: " & _
        mTanggalUltah.KeStringStandar()
    End Function ' KeStringStandar

End Class ' CKaryawan

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
' Kode 7.10: UjiKomposisi.vb
' Demonstrasi sebuah objek dengan referensi objek anggota.

Imports System.Windows.Forms

Module modUjiKomposisi

    Sub Main()
        Dim karyawan As New CKaryawan( _
            "Djumanggal", "Sianipar", 3, 21, 1950, 3, 12, 1975)

        MessageBox.Show(karyawan.KeStringStandar(), _
            "Menguji Karyawan Kelas")
    End Sub ' Main

End Module ' modUjiKomposisi



Gambar 7.7 Demonstrasi komposisi


Menggunakan Referensi Me
Setiap objek dapat mengakses sebuah referensi yang menunjuk kepada dirinya sendiri menggunakan referensi Me. Referensi Me dipakai secara implisit untuk menunjuk ke variabel instans, properti, dan metode suatu objek. Berikut akan disajikan sebuah contoh menggunakan referensi Me secara eksplisit dan implisit untuk menampilkan data Private sebuah objek.

Kelas CWaktu4 (kode 7.11) mendefinisikan tiga variabel instans Private, yaitu mJam, mMenit, dan mDetik (baris 5). Konstruktor (baris 8-14) menerima tiga argumen Integer untuk menginisialisasi sebuah objek CWaktu4. Perhatikan bahwa pada contoh ini, nama-nama parameter konstruktor (baris 8-9) identik dengan nama-nama variabel instans kelas (baris 5). Variabel lokal metode yang memiliki nama sama dengan variabel instans kelas akan menyembunyikan variabel instans di dalam skop metode tersebut. Namun, metode dapat memakai referensi Me untuk menunjuk ke variabel instans secara eksplisit. Baris 11-13 pada kode 7.11 mendemonstrasikan fitur ini.

Metode BangunString (baris 17-20) menghasilkan nilai balik berupa sebuah String yang diciptakan oleh suatu statemen yang menggunakan referensi Me secara eksplisit dan implisit. Baris 18 menggunakan referensi Me secara eksplisit untuk memanggil metode KeStringUniversal, sedangkan baris 19 menggunakan referensi Me secara implisit untuk memanggil metode KeStringUniversal. Perhatikan bahwa kedua baris melakukan tugas yang sama (yaitu, menghasilkan keluaran yang identik). Karena hal inilah mengapa programer biasanya tidak menggunakan referensi Me secara eksplisit untuk mereferensi metode.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
' Kode 7.11: CWaktu4.vb
' Enkapsulasi waktu menggunakan referensi Me.

Class CWaktu4
    Private mJam, mMenit, mDetik As Integer

    ' konstruktor CWaktu4
    Public Sub New(ByVal mJam As Integer, _
        ByVal mMenit As Integer, ByVal mDetik As Integer)

        Me.mJam = mJam
        Me.mMenit = mMenit
        Me.mDetik = mDetik
    End Sub ' New

    ' menciptakan String menggunakan referensi Me  eksplisit dan implisit
    Public Function BangunString() As String
        Return "Me.KeStringUniversal(): " & Me.KeStringUniversal() _
        & vbCrLf & "KeStringUniversal(): " & KeStringUniversal()
    End Function ' BangunString

    ' konversi menjadi String dalam format waktu-standar
    Public Function KeStringUniversal() As String
        Return String.Format("{0:D2}:{1:D2}:{2:D2}", _
            mJam, mMenit, mDetik)
    End Function ' KeStringUniversal

End Class ' CWaktu4

Module modUjiMe (kode 7.12) menjalankan aplikasi yang mendemonstrasikan kegunaan dari referensi Me. Baris 9 menginstansiasi sebuah instans dari kelas CWaktu4. Baris 11-12 memanggil metode BangunString, kemudian menampilkan hasil kepada pengguna di dalam MessageBox.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
' Kode 7.12: UjiMe.vb
' Demonstrasi referensi Me.

Imports System.Windows.Forms

Module modUjiMe

    Sub Main()
        Dim waktu As New CWaktu4(12, 30, 19)

        MessageBox.Show(waktu.BangunString(), _
            "Demonstrasi Referensi Me")
    End Sub ' Main

End Module ' modUjiMe



Gambar 7.8 Demonstrasi referensi Me


Anggota Kelas Shared
Setiap objek suatu kelas mempunyai salinan sendiri atas semua variabel instansnya. Namun, pada beberapa kasus, semua objek suatu kelas dapat memakai bersama satu salinan atas variabel tertentu. Variabel tersebut dinamakan dengan variabel kelas Shared; sebuah program hanya memuat satu salinan dari variabel ini di dalam memori, tidak peduli berapa banyak objek kelas diinstansiasi. Sebuah variabel kelas Shared merepresentasikan informasi rentang-kelas, dimana semua objek kelas memakai bersama suatu data. Deklarasi sebuah anggota Shared diawali dengan katakunci Shared.

Dalam Visual Basic, programer dapat mendefinisikan apa yang dikenal dengan konstruktor Shared, yang dipakai hanya untuk menginisialisasi anggota-anggota kelas Shared. Konstruktor Shared bersifat opsional dan harus dideklarasikan dengan katakunci Shared. Biasanya, konstruktor Shared dipakai ketika ia diperlukan untuk menginisialisasi sebuah variabel kelas Shared sebelum sembarang objek dari kelas tersebut diinstansiasi. Konstruktor Shared dipanggil sebelum sembarang anggota kelas Shared digunakan dan sebelum sembarang objek kelas diinstansiasi.

Meskipun variabel kelas Shared tampak seperti variabel global dalam C dan C++, hal ini tidak berlaku pada Visual Basic. Variabel kelas Shared memiliki skop kelas. Setiap anggota Public Shared suatu kelas dapat diakses melalui nama kelas menggunakan operator dot (yaitu, NamaKelas.namaAnggotaShared). Setiap anggota Private Shared suatu kelas hanya dapat diakses melalui metode kelas tersebut. Untuk mengakses anggota kelas Private Shared ketika tidak ada objek kelas yang diciptakan, programer harus menyediakan sebuah properti atau metode Public Shared.

Metode Shared tidak dapat mengakses anggota kelas tak-Shared. Tidak seperti metode tak-Shared, metode Shared tidak bisa memiliki referensi Me, karena variabel kelas Shared dan metode kelas Shared eksis secara independen dan tidak terikat oleh sembarang objek.

Kelas CKaryawan2 (kode 7.13) mendemonstrasikan penggunaan dari sebuah variabel kelas Private Shared dan sebuah properti Public Shared. Variabel kelas Shared, mHitung, diinisialisasi dengan nol secara default (baris 11). Variabek mHitung menjejak jumlah objek dari kelas CKaryawan2 yang telah diinstansiasi dan sekarang berada di dalam memori.

Ketika objek dari kelas CKaryawan2 eksis, anggota Shared, mHitung, dapat dipakai di dalam sembarang metode dari suatu objek CKaryawan2, dimana, pada contoh ini, konstruktor (baris 14-24) menginkremen mHitung (baris 20) dan metode Finalize (baris 27-30) mendekremen mHitung (baris 28). Perhatikan bahwa metode Finalize dideklarasikan menggunakan katakunci Protected dan Overrrides. Hal ini akan dijelaskan pada Bab 8 nanti. Jika tidak ada objek dari kelas CKaryawan2 yang eksis, jumlah mHitung dapat direferensi melalui pemanggilan terhadap Property Hitung (baris 53-59). Karena Property ini adalah Shared, Anda tidak perlu menginstansiasi objek CKaryawan2 untuk memanggil metode Get di dalam Property. Di samping itu, dengan mendeklarasikan Hitung sebagai ReadOnly, berarti Anda telah mencegah klien dari pengubahan nilai mHitung secara langsung, sehingga memastikan bahwa klien dapat mengubah nilai mHitung hanya melalui konstruktor CKaryawan2.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
' Kode 7.13: CKaryawan2.vb
' Kelas Karyawan2 menggunakan variabel Shared.

Class CKaryawan2
    Inherits Object

    Private mNamaPertama As String
    Private mNamaAkhir As String

    ' jumlah objek dalam memori
    Private Shared mHitung As Integer

    ' konstruktor CKaryawan2
    Public Sub New(ByVal nilaiNamaPertama As String, _
        ByVal nilaiNamaAkhir As String)

        mNamaPertama = nilaiNamaPertama
        mNamaAkhir = nilaiNamaAkhir

        mHitung += 1 ' menginkremen jumlah objek
        Console.WriteLine _
            ("Konstruktor objek Karyawan: " & mNamaPertama & _
            " " & mNamaAkhir)
    End Sub ' New

    ' metode finalizer mendekremen jumlah objek karyawan
    Protected Overrides Sub Finalize()
        mHitung -= 1 ' mendekremen mHitung
        Console.WriteLine _
            ("Finalizer objek Karyawan: " & mNamaPertama & _
            " " & mNamaAkhir & "; hitung = " & mHitung)
    End Sub ' Finalize

    ' menghasilkan nama pertama
    Public ReadOnly Property NamaPertama() As String

        Get
            Return mNamaPertama
        End Get

    End Property ' NamaPertama

    ' menghasilkan nama akhir
    Public ReadOnly Property NamaAkhir() As String

        Get
            Return mNamaAkhir
        End Get

    End Property ' NamaAkhir

    ' properti Hitung
    Public Shared ReadOnly Property Hitung() As Integer

        Get
            Return mHitung
        End Get

    End Property ' Hitung

End Class ' CKaryawan2

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
' Kode 7.14: UjiShared.vb
' Demonstrasi anggota-anggota Shared.

Imports System.Windows.Forms

Module modUjiShared

    Sub Main()
        Dim keluaran As String

        Console.WriteLine("Karyawan sebelum instansiasi: " & _
            CKaryawan2.Hitung)

        Dim karyawan1 As CKaryawan2 = _
            New CKaryawan2("Djumanggal", "Sianipar")

        Dim karyawan2 As CKaryawan2 = _
            New CKaryawan2("Undur", "Siahaan")

        ' keluaran dari karyawan2 setelah instansiasi
        Console.WriteLine(vbCrLf & _
            "Karyawan setelah instansiasi: " & vbCrLf & _
            "via CKaryawan2.Hitung: " & CKaryawan2.Hitung)

        ' menampilkan nama karyawan pertama dan karyawan kedua
        Console.WriteLine(vbCrLf & "Karyawan 1: " & _
            karyawan1.NamaPertama & " " & karyawan1.NamaAkhir & _
            vbCrLf & "Karyawan 2: " & karyawan2.NamaPertama & " " & _
            karyawan2.NamaAkhir)

        ' menandai karyawan1 dan karyawan2 untuk dihancurkan
        karyawan1 = Nothing
        karyawan2 = Nothing

        System.GC.Collect() ' meminta pengumpulan sampah memori
    End Sub ' Main

End Module ' modUjiShared

Karyawan sebelum instansiasi: 0
Konstruktor objek Karyawan: Djumanggal Sianipar
Konstruktor objek Karyawan: Undur Siahaan

Karyawan setelah instansiasi:
via CKaryawan2.Hitung: 2

Karyawan 1: Djumanggal Sianipar
Karyawan 2: Undur Siahaan
Finalizer objek Karyawan: Undur Siahaan; hitung = 1
Finalizer objek Karyawan: Djumanggal Sianipar; hitung = 0

Module modUjiShared (kode 7.14) menjalankan aplikasi yang mendemonstrasikan penggunaan anggota-anggota Shared (kode 7.13). Baris 11-12 menggunakan ReadOnly Shared Property Hitung dari kelas CKaryawan2 untuk mendapatkan nilai mHitung saat ini. Baris 14-18 kemudian menginstansiasi dua objek CKaryawan2, yang menginkremen nilai mHitung sebesar dua. Baris 26-29 menampilkan nama-nama karyawan. Baris 32-33 menetapkan setiap referensi yang menunjuk kepada kedua objek tersebut menjadi Nothing, sehingga referensi karyawan1 dan karyawan2 tidak lagi menunjuk ke objek CKaryawan2.


Anggota Const dan ReadOnly
Visual Basic membolehkan programer untuk menciptakan konstanta, atau anggota yang memiliki nilai yang tidak bisa diubah selama eksekusi program. Untuk menciptakan anggota data konstan suatu kelas, Anda bisa mendeklarasikannya menggunakan katakunci Const atau ReadOnly. Anggota data yang dideklarasikan sebagai Const harus diinisialisasi di dalam pendeklarasiannya; Anggota data yang dideklarasikan sebagai ReadOnly dapat diinisialisasi di dalam pendeklarasiannya atau di dalam konstruktor kelas. Nilai sebuah Const atau ReadOnly tidak dapat dimodifikasi setelah diinisialisasi.

Anggota yang dideklarasikan sebagai Const harus ditugasi nilai saat kompilasi. Oleh karena itu, anggota Const dapat diinisialisasi hanya dengan nilai konstanta, seperti integer, literal string, literal karakter, dan anggota Const lain. Anggota konstan dengan nilai yang tidak dapat ditentukan saat kompilasi harus dideklarasikan dengan katakunci ReadOnly. Telah disebutkan sebelumnya bahwa anggota ReadOnly dapat ditugasi sebuah nilai hanya sekali saja, saat dideklarasikan atau di dalam konstruktor kelas. Ketika dipilih untuk mendefinisikan anggota konstan di dalam sebuah konstruktor, konstruktor Shared harus dipakai untuk menginisialisasi anggota Shared ReadOnly, dan konstruktor tak-Shared digunakan untuk menginisialisasi anggota tak-Shared ReadOnly.

Kelas CKonstantaLingkaran (kode 7.15) mendemonstrasikan kegunaan konstanta. Baris 7 menciptakan konstanta PI menggunakan katakunci Const dan menugaskan nilai Double, 3.14159, kepadanya. Anda bisa saja menggunakan Const PI terdefinisi di dalam kelas Math (Math.PI), tetapi di sini Anda diminta mendemonstrasikan bagaimana menciptakan sebuah anggota data Const secara eksplisit. Nilai 3.14159 diterima pada baris 7, tetapi ekspresi

Convert.ToDouble( "3.14159" )

akan menghasilkan error sintaks jika digunakan. Meskipun ekspresi itu menggunakan sebuah nilai konstan (literal String3.14159”) sebagai argumen, error sintaks akan terjadi, karena kompiler tidak dapat mengevaluasi statemen Convert.ToDouble. Pembatasan ini berlaku untuk anggota ReadOnly. Perhatikan bahwa baris 14 (pada saat program dijalankan) menugaskan nilai dari parameter konstruktor nilaiRadius kepada anggota ReadOnly, mRadius.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
' Kode 7.15: CKonstantaLingkaran.vb
' Enkapsulasi konstanta PI dan radius.

Class CKonstantaLingkaran

    ' PI adalah anggota data konstan
    Public Const PI As Double = 3.14159

    ' radius adalah konstanta tak-terinisialisasi
    Public ReadOnly RADIUS As Integer

    ' konstruktor dari kelas CKonstantaLingkaran
    Public Sub New(ByVal nilaiRadius As Integer)
        RADIUS = nilaiRadius
    End Sub ' New

End Class ' CKonstantaLingkaran

Module modConstDanReadOnly (kode 7.16) mengilustrasikan kegunaan Const dan ReadOnly. Baris 9-11 menggunakan kelas Random untuk membangkitkan Integer acak antara 1-20. Baris 11 melewatkan nilai ini kepada konstruktor CKonstantaLingkaran untuk menginstansiasi sebuah objek CKonstantaLingkaran. Baris 13 kemudian mengakses variabel ReadOnly, mRadius, melalui sebuah referensi yang menunjuk ke instans kelasnya. Baris 15-17 menghitung keliling lingkaran dan menugaskan nilainya kepada String keluaran. Kalkulasi ini menggunakan anggota Const, PI, yang diakses pada baris 17 melalui referensi kelas Shared. Baris 19-20 menampilkan nilai radius dan keliling lingkaran di dalam sebuah MessageBox.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
' Kode 7.16: ConstDanReadOnly.vb
' Demonstrasi anggota-anggota Const dan ReadOnly.

Imports System.Windows.Forms

Module modConstDanReadOnly

    Sub Main()
        Dim acak As Random = New Random()
        Dim lingkaran As CKonstantaLingkaran = _
            New CKonstantaLingkaran(acak.Next(1, 20))

        Dim radius As String = Convert.ToString(lingkaran.RADIUS)

        Dim keluaran As String = "Radius = " & radius & vbCrLf _
            & "Keliling Lingkaran = " + String.Format("{0:N3}", _
            lingkaran.RADIUS * 2 * CKonstantaLingkaran.PI)

        MessageBox.Show(keluaran, "Keliling Lingkaran", _
            MessageBoxButtons.OK, MessageBoxIcon.Information)
    End Sub ' Main

End Module ' modConstDanReadOnly



Gambar 7.9 Demonstrasi anggota kelas Const dan ReadOnly


Namespace dan Assembly
Namespace dapat dipakai untuk meminimalkan masalah konflik penamaan. Dua kelas pada suatu namespace tidak dapat memiliki nama sama, tetapi namespace yang berbeda dapat memuat kelas-kelas dengan nama sama. Dengan jutaan orang menulis program Visual Basic, nama yang dipilih seorang programer untuk sebuah kelas bisa jadi konflik dengan nama yang dipilih oleh programer untuk kelas buatannya.

Kode 7.17, yang menyediakan kode untuk kelas CKaryawan3, mendemonstrasikan penciptaan suatu pustakan kelas (class library) yang dapat didaur-ulang. Perhatikan bahwa kelas ini identik dengan kelas CKaryawan2 (kode 7.13), kecuali bahwa kelas CKaryawan3 dideklarasikan sebagai kelas Public. Ketika projek lain menggunakan sebuah pustaka kelas, hanya kelas Public yang dapat diakes. Jadi, jika Anda tidak mendeklarasikan CKaryawan3 sebagai Public, maka projek lain tidak akan bisa menggunakannya. Akan didemonstrasikan bagaimana memaketkan kelas CKaryawan3 ke dalam PustakaKaryawan.dll, yang merupakan dynamic link library yang dapat didaur-ulang (digunakan kembali) oleh projek lain.


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
' Kode 7.17: CKaryawan3.vb
' Kelas CKaryawan3 menggunakan variabel Shared.

Public Class CKaryawan3
    Inherits Object

    Private mNamaPertama As String
    Private mNamaAkhir As String

    ' jumlah objek dalam memori
    Private Shared mHitung As Integer

    ' konstruktor CKaryawan2
    Public Sub New(ByVal nilaiNamaPertama As String, _
        ByVal nilaiNamaAkhir As String)

        mNamaPertama = nilaiNamaPertama
        mNamaAkhir = nilaiNamaAkhir

        mHitung += 1 ' menginkremen jumlah objek
        Console.WriteLine _
            ("Konstruktor objek Karyawan: " & mNamaPertama & _
            " " & mNamaAkhir)
    End Sub ' New

    ' metode finalizer mendekremen jumlah objek karyawan
    Protected Overrides Sub Finalize()
        mHitung -= 1 ' mendekremen mHitung
        Console.WriteLine _
            ("Finalizer objek Karyawan: " & mNamaPertama & _
            " " & mNamaAkhir & "; hitung = " & mHitung)
    End Sub ' Finalize

    ' menghasilkan nama pertama
    Public ReadOnly Property NamaPertama() As String

        Get
            Return mNamaPertama
        End Get

    End Property ' NamaPertama

    ' menghasilkan nama akhir
    Public ReadOnly Property NamaAkhir() As String

        Get
            Return mNamaAkhir
        End Get

    End Property ' NamaAkhir

    ' properti Hitung
    Public Shared ReadOnly Property Hitung() As Integer

        Get
            Return mHitung
        End Get

    End Property ' Hitung

End Class ' CKaryawan3

Sekarang akan dideskripsikan bagaimana menciptakan sebuah pustaka kelas yang memuat kelas CKaryawan3:
1.       Ciptakan sebuah projek pustaka kelas. Pilih File > New > Project... untuk menampilkan dialog New Project. Pilih Visual Basic dari Project types, kemudian pilih Class Library dari Templates. Berikan nama projek dengan PustakaKaryawan, dan pilih sebuah direktori yang di dalamnya Anda akan menempatkan projek Anda. Pustaka kelas yang diciptakan ditampilkan pada Gambar 7.10. Ada dua hal penting tentang kode pustaka kelas. Yang pertama adalah bahwa tidak terdapat metode Main. Ini mengindikasikan bahwa sebuah pustaka kelas bukanlah program yang dapat dieksekusi, yang tidak didesain sebagai aplikasi yang bisa berdiri sendiri. Yang kedua adalah bahwa Class1 adalah kelas Public, sehingga ia dapat diakses oleh projek lain.



Gambar 7.10 Projek pustaka kelas (Class Library) sederhana


2.       Pada Solution Explorer, namai-ulang Class1.vb dengan CKaryawan3.vb (dengan mengklik-kanan pada Class1.vb dan pilih Rename). Ganti kode yang dibangkitkan oleh IDE Visual Studio berikut:

Public Class Class1

End Class

dengan kode dari kelas CKaryawan3 (kode 7.17).

3.       Pilih Build > Build Solution untuk mengkompilasi kode. Ingat bahwa kode ini tidak dapat dieksekusi. Jika programer mencoba untuk mengeksekusi pustaka kelas dengan memilih  Debug > Start Without Debugging, maka Visual Studio akan menampilkan pesan error.

Ketika pustaka kelas berhasil dikompilasi, sebuah assembly akan diciptakan. Assembly ini berada di dalam direktori bin, dan secaa default dinamakan PustakaKaryawan.dll. File assembly ini memuat kelas CKaryawan3, yang dapat dipakai oleh modul, kelas, dan projek lain. File assembly, yang berekstensi .dll dan .exe, merupakan inti dari pengembangan aplikasi Visual Basic. Sistem operasi Windows menggunakan file executable (.exe) untuk menjalankan aplikasi dan file pustaka (.dll) untuk menciptakan pustaka kode.

Module modUjiAssembly (kode 7.18) mendemonstrasikan penggunaan file assembly. Module menggunakan kelas CKaryawan3 di dalam PustakaKaryawan.dll untuk menciptakan objek CKaryawan3. Sebuah referensi yang menunjuk ke assembly diciptakan dengan memilih Project > Add Reference. Gunakan tombol Browse, pilih PustakaKaryawan.dll (berlokasi di dalam direktori bin pada projek PustakaKaryawan, kemudian klik OK untuk menambahkan resource tersebut ke dalam projek. Begitu referensi telah ditambahkan, digunakan katakunci Imports diikuti dengan nama namespace (PustakaKaryawan) untuk memberitau kompiler bahwa Anda sedang menggunakan kelas dari namespace ini.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
' Kode 7.18: UjiAssembly.vb
' Demonstrasi file assembly dan namespace

Imports PustakaKaryawan

Module modUjiAssembly

    Sub Main()
        Dim keluaran As String

        Console.WriteLine("Karyawan sebelum instansiasi: " & _
            CKaryawan3.Hitung)

        Dim karyawan1 As CKaryawan3 = _
            New CKaryawan3("Djumanggal", "Sianipar")

        Dim karyawan2 As CKaryawan3 = _
            New CKaryawan3("Undur", "Siahaan")

        ' keluaran dari karyawan2 setelah instansiasi
        Console.WriteLine(vbCrLf & _
            "Karyawan setelah instansiasi: " & vbCrLf & _
            "via CKaryawan3.Hitung: " & CKaryawan3.Hitung)

        ' menampilkan nama karyawan pertama dan karyawan kedua
        Console.WriteLine(vbCrLf & "Karyawan 1: " & _
            karyawan1.NamaPertama & " " & karyawan1.NamaAkhir & _
            vbCrLf & "Karyawan 2: " & karyawan2.NamaPertama & " " & _
            karyawan2.NamaAkhir)

        ' menandai karyawan1 dan karyawan2 untuk dihancurkan
        karyawan1 = Nothing
        karyawan2 = Nothing

        System.GC.Collect() ' meminta pengumpulan sampah memori
    End Sub ' Main

End Module ' modUjiAssembly

Karyawan sebelum instansiasi: 0
Konstruktor objek Karyawan: Djumanggal Sianipar
Konstruktor objek Karyawan: Undur Siahaan

Karyawan setelah instansiasi:
via CKaryawan3.Hitung: 2

Karyawan 1: Djumanggal Sianipar
Karyawan 2: Undur Siahaan
Finalizer objek Karyawan: Undur Siahaan; hitung = 1
Finalizer objek Karyawan: Djumanggal Sianipar; hitung = 0


Latihan
1.       Modifikasilah kelas CHari pada kode 7.8 untuk melakukan pemeriksaan error pada nilai-nilai penginisialisasi untuk variabel instans mBulan, mHari, dan mTahun. Di samping itu, sediakan sebuah metode HariBerikutnya untuk menginkremen hari sebesar satu. Objek CHari harus selalu memiliki nilai yang valid. Tulislah sebuah program untuk menguji metode HariBerikutnya di dalam suatu loop yang menampilkan tanggal pada tiap iterasi sehingga mengilustrasikan bahwa metode HariBerikutnya bekerja dengan benar. Pastikan untuk menguji dua kasus berikut:
a)       Menginkremen ke bulan berikutnya.
b)      Menginkremen ke tahun berikutnya.

2.       Tulislah sebuah aplikasi konsol yang mengimplementasikan kelas CPersegi. Kelas CPersegi harus memuat sebuah properti Sisi untuk mengakses data Private. Sediakan dua konstruktor: satu konstruktor tanpa argumen dan satu lagi mengambil sebuah argumen panjang Sisi.

3.       Ciptakan sebuah kelas CAkunSimpanan. Gunakan sebuah variabel kelas Shared untuk menyimpan mSukuBungaTahunan untuk semua pemegang akun. Setiap objek dari kelas tersebut memuat sebuah variabel instans Private, mSaldoSimpanan, yang mengindikasi-kan jumlah simpanan pada deposit. Sediakan metode HitungBungaBulanan untuk menghitung bunga per bulan dengan mengalikan mSaldoSimpanan dengan mSukuBungaTahunan dibagi dengan 12; suku bunga ini kemudian ditambahkan ke mSaldoSimpanan. Sediakan metode Shared, ModifikasiSukuBunga, untuk menetapkan mSukuBungaTahunan menjadi nilai baru. Tulislah sebuah program untuk menguji kelas CAkunSimpanan. Instansiasilah dua objek CAkunSimpanan, penabung1 dan penabung2, dengan saldo Rp. 100 dan Rp. 300. Tetapkan mSukuBungaTahunan menjadi 4%, kemudian hitung bunga per bulan dan tampilkan nilai saldo baru untuk tiap penabung. Kemudian tetapkan mSukuBungaTahunan menjadi 5% dan tampilkan kembali nilai saldo baru untuk tiap penabung.




No comments:

Post a Comment