Halo! Selamat datang kembali di “Seri Belajar Dasar Pemrograman Bahasa C#“. Pada materi sebelumnya, Anda sudah mempelajari tentang bagaimana bekerja dengan tipe data string di C#. Materi yang cukup panjang, bukan?
Kali ini, kita akan mempelajari bagaimana mengubah nilai variabel dari tipe data tertentu menjadi nilai variabel dari tipe data yang lain. Untuk mempelajari materi ini, pastikan Anda sudah memahami apa itu tipe data dan variabel.
Setelah mempelajari materi ini, Anda akan memahami kapan sebuah tipe bisa dikonversi secara implisit dan kapan konversi eksplisit harus dilakukan. Selain itu, Anda juga akan mengerti cara menggunakan beberapa operasi bawaan C# yang bisa digunakan untuk mengkonversi tipe data. Terakhir, Anda juga akan mengerti bagaimana melakukan parsing terhadap sebuah masukan dari tipe string
dan mengkonversinya ke tipe data yang diperlukan.
Apa Perlunya Mengkonversi Tipe Data?
Ketika kita sudah mendeklarasikan sebuah variabel dari tipe data tertentu, terkadang setelahnya kita perlu merubah tipe data dari nilai yang disimpan di dalam variabel tersebut ke tipe data yang lain.
Katakanlah kita diminta untuk membuat aplikasi kalkulator sederhana. Input angka dari keyboard yang diberikan oleh pengguna aplikasi tersebut sebenarnya masih berupa sebuah teks (tipe data string
). Namun, kita ingin menggunakan nilai input tersebut untuk melakukan operasi aritmatika seperti penjumlahan, pengurangan, pembagian, dan perkalian.
Apakah mungkin melakukan operasi perkalian pada sebuah nilai dari tipe data string
? Tentunya tidak, bukan? Untuk melakukan operasi aritmatika, kita membutuhkan nilai variabel dari tipe bilangan numerik, misalnya int
. Oleh karena itu, mengkonversi tipe data dari string
ke int
harus dilakukan terlebih dahulu sebelum melakukan operasi aritmatika pada nilai-nilai variabel tersebut.
Satu hal lagi yang perlu diperhatikan pada saat melakukan konversi tipe data adalah ukuran dari masing-masing tipe data yang akan kita gunakan. Mengkonversi tipe data suatu variabel dari satu tipe data ke tipe data yang lain, tak hanya mengubah tipe datanya saja, namun juga ikut mengubah ukuran maksimum dari variabel tersebut.
Misalnya, tipe data int
memiliki ukuran 4 byte. Artinya, tipe data int
bisa menampung sebuah nilai numerik dari -2,147,483,648 sampai 2,147,483,647. Nilai numerik di luar rentang nilai tersebut tidak bisa ditampung oleh tipe data int
.
Konversi antar tipe data bisa dilakukan dengan dua cara, yaitu secara implisit dan eksplisit.
Konversi Tipe Data Secara Implisit
Yang dimaksud dengan konversi secara implisit adalah ketika compiler mampu melakukan konversi tanpa perlu diberi instruksi apapun untuk melakukan konversi.
Tidak semua konversi bisa dilakukan secara implisit. C# hanya akan melakukan konversi secara implisit selama hal itu dimungkinkan.
Lalu, kondisi-kondisi seperti apa saja yang memungkinkan terjadinya konversi tipe data secara implisit?
1. konversi secara implisit dimungkinkan apabila tipe data yang akan dikonversi memiliki ukuran atau rentang nilai yang lebih kecil daripada tipe data hasil konversi.
Contohnya, tipe data int
memiliki ukuran 4 Byte sedangkan tipe data double
memiliki ukuran 8 Byte. Oleh karena itu tipe data int
bisa dikonversi ke tipe data double
secara implisit. Namun, tidak sebaliknya.
int variabelInt = 2147483647;
double variabelDouble = variabelInt;
Pada potongan kode program di atas, compiler akan mengkonversi nilai variabel variabelInt
yang bertipe data int
secara implisit. Proses konversi implisit dari tipe data dengan ukuran yang lebih kecil ke tipe data dengan ukuran yang lebih besar biasa disebut dengan operasi pelebaran atau widening operation.
Sedangkan potongan kode program di bawah, akan menghasilkan eror yang menyatakan bahwa compiler tidak bisa melakukan konversi secara implisit dari double
ke int
.
double variabelDouble = 2147483647;
int variabelInt = variabelDouble;
Percobaan melakukan konversi implisit dari tipe data dengan ukuran yang lebih besar ke tipe data dengan ukuran yang lebih kecil seperti di atas biasa disebut dengan operasi penyempitan atau narrowing operation. Operasi penyempitan secara impisit akan selalu menghasilkan eror.

2. konversi secara implisit hanya bisa dilakukan antar tipe data yang sepadan, misalnya sama-sama merupakan tipe bilangan numerik (double
, int
).
Tipe string
dan tipe int
bukan merupakan tipe data yang sepadan karena tipe string
merupakan teks, sedangkan tipe int
merupakan bilangan numerik. Oleh karena itu, compiler tidak bisa mengkonversi tipe data string
menjadi int
secara implisit.
string variabelString = Console.ReadLine();
int variabelInt = variabelString;
Potongan kode program di atas akan menghasilkan eror seperti pada gambar di bawah ini.

Konversi Tipe Data Secara Eksplisit
Apabila kedua kondisi di mana konversi secara implisit dimungkinkan tidak terpenuhi, maka kita harus menggunakan konversi secara eksplisit. Konversi secara eksplisit ini biasa disebut dengan casting.
Di C#, casting bisa dilakukan dengan tiga cara, yaitu dengan menggunakan type modifier di depan variabel yang tipe datanya ingin diubah, menggunakan method yang disediakan oleh .NET di dalam class Convert
, dan menggunakan method TryParse()
atau Parse()
.
Perhatian
Method TryParse() dan Parse() hanya bisa digunakan untuk mengkonversi tipe string saja. Parsing sendiri berarti mengurai, artinya method tersebut akan mengurai sebuah teks/string karakter demi karakter dan kemudian mengkonversi karakter-karakter tersebut menjadi bilangan numerik atau boolean.
Menggunakan Pengubah Tipe (Type Modifier)
Untuk melakukan casting menggunakan pengubah tipe (type modifier), kita cukup menuliskan tipe data baru yang diinginkan, di depan variabel yang ingin kita ubah tipe datanya, dengan tanda kurung.
double varDouble = 1234.6;
int varInt;
// Mengkasting double ke int dengan cara menempatkan pengubah tipe (type modifier) tepat
// di depan tipe yang akan dikonversi, di dalam kurung.
varInt = (int)varDouble;
Nilai dari varInt
adalah 1234.
Menggunakan Method Dari Class Convert
Class Convert
menyediakan beberapa method yang dapat digunakan untuk mengubah suatu tipe data ke tipe data yang lain seperti pada tabel di bawah ini.
METHOD | DESKRIPSI |
ToBoolean() | Mengkonversi suatu nilai tertentu ke sebuah nilai boolean |
ToByte() | Mengkonversi suatu nilai tertentu ke sebuah nilai integer 8-bit |
ToChar() | Mengkonversi suatu nilai tertentu ke sebuah karakter unicode |
ToDateTime() | Mengkonversi suatu nilai tertentu ke sebuah nilai tanggal dan waktu |
ToDecimal() | Mengkonversi suatu nilai tertentu ke sebuah nilai desimal |
ToDouble() | Mengkonversi suatu nilai tertentu ke sebuah angka floating dengan presisi double |
ToInt16() | Mengkonversi suatu nilai tertentu ke sebuah nilai integer positif 16-bit |
ToInt32() | Mengkonversi suatu nilai tertentu ke sebuah nilai integer positif 32-bit |
ToInt64() | Mengkonversi suatu nilai tertentu ke sebuah nilai integer positif 64-bit |
ToSByte() | Mengkonversi suatu nilai tertentu ke sebuah nilai integer positif 8-bit |
ToSingle() | Mengkonversi suatu nilai tertentu ke sebuah angka floating dengan presisi single |
ToUInt16() | Mengkonversi suatu nilai tertentu ke sebuah nilai integer 16-bit |
ToUInt32() | Mengkonversi suatu nilai tertentu ke sebuah nilai integer 32-bit |
ToUInt64() | Mengkonversi suatu nilai tertentu ke sebuah nilai integer 64-bit |
Potongan kode program di bawah ini mendemonstrasikan bagaimana menggunakan method dari class Convert
untuk mengkonversi suatu nilai.
double varDouble = 1234.6;
int varInt;
// Mengkasting double ke int dengan menggunakan class Convert dan method ToInt32.
// Ini mengkonversi nilai double ke 32-bit signed integer.
varInt = Convert.ToInt32(varDouble);
Kali ini nilai dari varInt
adalah 1235.
Menggunakan Parse() dan TryParse()
Baik Parse()
maupun TryParse()
hanya bisa digunakan untuk mengkonversi nilai string
ke nilai tipe tertentu (misal, numerik atau boolean).
Potongan kode program di bawah ini mendemonstrasikan bagaimana menggunakan method Parse()
.
// mengkonversi string ke int
string intString = "12345";
int varInt = int.Parse(intString);
// mengkonversi string ke double
string doubleString = "12345.678";
double varDouble = double.Parse(doubleString);
// mengkonversi string ke boolean
string boolString = "true";
bool varBool = bool.Parse(boolString);
Kita bisa mengganti Parse()
dengan TryParse()
dan menghasilkan nilai konversi yang sama. Lalu apa bedanya? TryParse()
akan menghasilkan nilai boolean false apabila gagal melakukan konversi. Sedangkan Parse()
akan menghasilkan eksepsi apabila gagal melakukan konversi (aplikasi Anda biasanya akan mengalami crash apabila sebuah eksepsi tidak ditangani).
// mengkonversi string ke int dengan Parse()
string intString = "f12345";
int varInt = int.Parse(intString);
Kode program di atas akan menghasilkan eksepsi karena huruf f gagal dikonversi menjadi nilai integer.

Sekarang kita coba melakukan konversi dengan TryParse()
untuk nilai input string yang sama. Kira-kira apa yang terjadi?
string intString = "f12345";
int varInt;
bool berhasilParsing = int.TryParse(intString, out varInt);
if (berhasilParsing)
{
Console.WriteLine(varInt);
}
else
{
Console.WriteLine("Parsing gagal");
}
Console.ReadLine();
Pertama-tama TryParse()
akan mencoba mengkonversi nilai string yang tersimpan di variabel intString
. Jika berhasil, TryParse()
akan menghasilkan nilai boolean true dan hasil konversi dari nilai string
ke int
akan disimpan di dalam parameter out varInt
. Jika gagal, TryParse()
akan menghasilkan nilai boolean false. Nilai boolean tersebut kemudian disimpan di dalam variabel dari tipe bool
bernama berhasilParsing
.
Catatan
Kita akan mempelajari pengubah parameter out di materi “Pengubah Parameter Pada Method Di C#“
Kemudian, jika berhasilParsing
bernilai true (proses parsing berhasil), maka nilai varInt
akan ditampilkan. Namun, jika berhasilParsing
bernilai false, maka “Parsing gagal” akan ditampilkan di layar console.
Karena TryParse()
gagal mengkonversi huruf f menjadi nilai integer, maka TryParse()
akan menghasilkan nilai false. Sehingga yang ditampilkan di layar adalah seperti gambar berikut ini.

Signed Overflow
Pada saat melakukan konversi tipe data, kita benar-benar perlu memperhatikan rentang nilai dari masing-masing tipe data yang terlibat dalam proses konversi.
Jika kita abai, meskipun proses konversi tidak menghasilkan eror, namun hasil yang kita dapatkan bisa saja di luar ekspektasi seperti pada contoh berikut ini.
short angka1 = 30000;
short angka2 = 30000;
// operator + mengkonversi operand ke tipe int secara implisit.
// Oleh krena itu, kita perlu mengkonversinya kembali ke tipe short secara eksplisit.
short jumlahShort = (short)(angka1 + angka2);
Console.WriteLine("jumlahShort = {0}", jumlahShort);
Ekspektasi kita, variabel jumlahShort
mestinya bernilai 60000, bukan?
Kenyataannya , variabel jumlahShort
di atas akan bernilai -5536. Hal ini sebenarnya tidak aneh karena tipe data short
hanya bisa menampung nilai dengan rentang -32767~32767. Nilai 60000 jelas berada di luar rentang nilai tipe data short
.
Tapi mengapa keluarannya bisa menghasilkan angka -5536?
Apabila kita menggunakan aplikasi kalkulator dengan mode programmer, angka 60000 nilainya sama dengan bilangan biner 1110 1010 0110 0000. Satu angka di dalam bilangan biner merepresentasikan 1 bit data. Jadi, bilangan biner 1110 1010 0110 0000 merepresentasikan 16 bit data. Tipe data short
merupakan tipe data signed 16-bit. Signed berarti bahwa tipe data ini memiliki rentang nilai dari bilangan negatif sampai bilangan positif (-32767~32767).

Angka paling kiri pada bilangan biner dengan rentang negatif-positif merepresentasikan tanda (sign) positif atau negatif. Angka 1 merepresentasikan tanda minus (negatif) dan angka 0 merepresentasikan tanda plus (positif).
Untuk merubah bilangan biner di atas ke bilangan desimal, kita bisa melakukan perhitungan seperti berikut ini.
-215 + 214 + 213 + 211 + 29 + 26 + 25 = -32768 + 16384 + 8192 + 2048 + 512 + 64 + 32 = -5536
Bilangan pangkat di atas merepresentasikan posisi bit tiap-tiap data. Posisi bit paling kiri adalah 15 dan bit paling kanan adalah 0. Pada perhitungan di atas, kita hanya menghitung bit dengan nilai 1 saja karena nilai 0 dengan pangkat berapapun akan tetap bernilai 0. Angka 2 berarti bahwa tiap bit data merupakan bilangan biner (sistem bilangan yang hanya terdiri dari 2 angka, yaitu 0 dan 1).
Karena bit paling kiri bernilai 1, maka kita perlu menambahkan tanda minus di depan angka 2. Jika semua bit kita jumlahkan, maka perhitungan di atas akan menghasilkan angka -5536.
Fenomena di atas biasa disebut dengan signed overflow, di mana nilai yang dihasilkan dari proses konversi pada tipe data dengan rentang negatif-positif melebihi daya tampung yang disediakan, dalam kata lain “meluap” atau overflowing.
Unsigned Overflow
Selain pada tipe signed seperti short
, overflow juga bisa terjadi pada tipe unsigned seperti tipe byte
. Tipe byte
merupakan tipe data unsigned 8-bit. Unsigned berarti bahwa tipe ini memiliki rentang nilai pada bilangan positif saja. Ukuran 8-bit berarti bahwa tipe ini memiliki rentang nilai dari angka 0 sampai dengan 255.
Coba perhatikan baris kode program di bawah ini.
byte b1 = 100;
byte b2 = 250;
byte jml = (byte)(b1 + b2);
Console.WriteLine("jml = {0}", jml);
Kira-kira berapa nilai dari variabel jml
yang ditampilkan ke layar console?
Mungkin Anda akan menjawab 350, tapi sayangnya jawaban tersebut tidak tepat.
Jangan kaget apabila nilai dari variabel jml
adalah 94. Iya, bukan 350 melainkan 94.
Ingat bahwa tipe data byte
hanya bisa menampung angka 0 sampai 255. Angka 350 jelas akan “meluap” karena daya tampung tipe byte
terlalu kecil untuk menampung angka tersebut.
Lalu mengapa hasilnya menjadi 94?
Apabila Anda kembali menggunakan kalkulator dengan mode programming, angka 350 akan menghasilkan bilangan biner 0001 0101 1110. Angka biner yang dihasilkan berukuran 12-bit (bit ke-0 ~ bit ke-11).
Karena tipe byte
hanya berukuran 8-bit, maka bit ke-8 sampai dengan bit ke-11 tidak bisa ditampung oleh tipe byte
. Dengan demikian, hanya 8-bit paling kanan, yaitu 0101 1110, yang akan ditampung oleh tipe byte
.
Apabila bilangan biner 0101 1110 kita konversi ke bilangan desimal, maka bilangan biner tersebut akan menghasilkan angka 94.
26 + 24 + 23 + 22 + 21 = 64 + 16 + 8 + 4 + 2 = 94
Fenomena di atas biasa disebut dengan unsigned overflow.
Menggunakan Ekspresi Checked
Mendapatkan keluaran di luar ekspektasi tentunya bukanlah sesuatu yang kita inginkan. Oleh karena itu kita membutuhkan sebuah mekanisme untuk memastikan bahwa proses konversi tidak terjadi overflow. Di C#, kita bisa menggunakan ekspresi checked
.
Ekspresi ini akan mengecek apakah terjadi overflow pada suatu operasi konversi atau tidak. Jika terjadi overflow, ekspresi ini akan melontarkan sebuah eksepsi yang perlu kita tangani dengan blok try-catch seperti kode program di bawah ini.
try
{
jml = checked((byte)(b1 + b2));
Console.WriteLine("jml = {0}", jml);
}
catch (OverflowException ex)
{
Console.WriteLine(ex.Message); // arithmetic operation resulted in an overflow
}
Pertama-tama, kode program di dalam blok try
akan dieksekusi. Apabila terjadi overflow pada operasi (byte)(b1 + b2)
, maka ekspresi checked
akan melontarkan sebuah eksepsi yang akan “ditangkap” atau ditangani oleh kode program di dalam blok catch
.
Untuk saat ini, Anda tidak perlu khawatir dengan konstruksi try-catch di atas. Konstruksi ini akan kita pelajari bersama di dalam materi tentang bagaimana menangani sebuah ekspesi.
Penutup
Di C#, konversi tipe data dilakukan dengan dua cara, yaitu secara implisit dan eksplisit.
Untuk melakukan konversi tipe data secara eksplisit, kita bisa menggunakan type modifier, method dari class Convert
, dan juga Parse()
/ TryParse()
.
Proses konversi secara eksplisit bisa menghasilkan nilai di luar ekspektasi apabila terjadi overflow. Kita bisa menggunakan ekspresi checked
untuk memastikan bahwa hanya nilai yang sesuai dengan ekspektasi saja yang dihasilkan dan melontarkan eksepsi apabila terjadi overflow.
Itu saja materi kita kali ini. Jika Anda merasa kesulitan dalam memahami materi ini, jangan menyerah! Tulis kesulitan atau pertanyaan Anda di kolom komentar, saya akan membantu.
Selamat belajar!