Menyelesaikan Isogram Menggunakan Ruby

Akhir pekan kemarin saya main ke Jakarta buat datang acara Python Conference Indonesia 2018. Perjalanan naik kereta dari Yogyakarta ke Jakarta makan waktu yang lama, hampir 8 jam. Di sela-sela waktu selama itu saya sempatkan buat main-main ngoding problem solving di https://exercism.io/.

Ada satu kasus yang menarik karena saya bisa menyelesaikannya menggunakan 2 cara. Cara pertama cukup bertele-tele logikanya sedangkan yang kedua sangat simpel. Kasusnya adalah terkait isogram. Kita diminta untuk menentukan apakah suatu kata termasuk isogram atau bukan. Isogram itu kata yang tidak memiliki huruf yang berulang. tes termasuk isogram, test bukan isogram karena huruf t muncul lebih dari satu kali.

Dari file test yang diberikan, yang digunakan untuk mengetahui apakah kodingan kita sudah benar atau belum, terdapat contoh inputan "six-year-old" yang tetap dianggap isogram, artinya huruf saja yang diperhatikan. Ada juga contoh input "Emily Jung Schwartzkopf" yang lagi-lagi termasuk isogram, berarti spasi bisa dihiraukan.

Kuy kita berpetualang bareng menyelesaikan kasus ini.

Penyelesaian Pertama

Dari contoh test yang diberikan yang sudah saya bahas sebelumnya, kita bisa menentukan kalau kita butuh untuk menghilangkan tanda - dan juga spasi. Atau dalam kalimat lain adalah diambil saja katanya. Dari sini kita bisa buat sebuah private method seperti ini.

Di sini kita pakai regex /\w+/ untuk hanya mengambil word/kata saja.

Cara pertama yang saya buat ini logikanya seperti ini.

1. Buat input yang ada jadi satu string tanpa spasi, tanpa tanda - kemudian setiap hurunya adalah elemen array. Ini kita capai dengan method array_of_letters yang ada di atas tadi.
2. Buat dictionary untuk menghitung kemunculan suatu huruf.
3. Dari dictionary yang ada, tentukan apakah TIDAK ADA huruf yang muncul lebih dari 1 kali

Dengan langkah 2 kita terapkan di kode, sekarang kelas Isogram jadi seperti ini

Idenya adalah, yang jadi key adalah huruf di suatu string dan value-nya adalah nilai kemunculan berupa angka. Untuk ngasih nilai default 0, digunakan dictionary = Hash.new(0).

Selanjutnya dilakukan looping terhadap string yang sudah kita susun biar jadi hanya satu string. Di dalam looping kita hitung nilai kemunculan. Perhatikan adanya letter.downcase. Ini saya buat biar antara huruf kapital dan non kapital dianggap sama. Penggunaan downcase bisa digunakan di saat kita membuat satu gabungan string juga. Seperti ini.

Bebas pilih yang mana.

Langkah terakhir kita tentukan, dari dictionary tadi apakah TIDAK ADA yang kemunculan hurufnya lebih dari satu. Kalau ada otomatis akan mengembalikan false yang artinya kata atau kalimat bukan sebuah isogram.

Perubahan kode bisa dilihat dengan adanya method baru bernama no_more_than_one_word?.

Simple bukan cara ngitungya? Kita pakai method select dan masukan syaratnya gimana. Terus pakai empty? biar tahu, ada atau tidak yang jumlah kemunculan > 1.

Penyelesaian Kedua

Cara ini saya dapat setelah mikir-mikir lagi. Cara pertama rasanya muter-muter, masa ga ada cara lain yang lebih cantik?

Terus kepikiran gini. Bukankah kita bisa tahu suatu kata atau kalimat itu isogram atau bukan dengan membandingkan apakah huruf penyusunnya yang unik (tidak muncul lebih dari 1 kali) sama dengan bentuk asli kata/kalimat tersebut?.

Dari sini, didapatkan kode seperti di bawah.

Di ruby kita bisa dapatkan elemen unik dari array menggunakan method uniq. Dari situ bisa langsung kita bandingkan dengan bentuk aslinya. Tampak di array_of_letters(input).uniq == array_of_letters(input)

Gimana? Jauh lebih simple cara yang kedua ini kan 😄

Facebook Comments
 

Agung Setiawan

Agung Setiawan adalah software engineer di BukaLapak.com, penulis sekaligus pecinta sastra, dan pembaca buku

 
Halo, perkenalkan saya Agung Setiawan.
Saya Software Engineer di BukaLapak.
Simak pemikian saya soal dunia Software Engineering via Twitter di @agungsetiawanmu dan facebook
Blog ini saya update seminggu sekali jadi sering-sering saja mampir
Mau belajar Vim bareng saya?
Belajar ngoding dari nol menggunakan PHP

Leave a Reply

Your email address will not be published. Required fields are marked *