Saya sedang menulis kode Ruby untuk latihan enkripsi sederhana dan sering mengalami dilema ini (latihan ini adalah sandi solitaire jika Anda harus tahu). Ini adalah pertanyaan apakah saya harus menggunakan logika saya dengan variabel deskriptif dan pernyataan satu langkah yang membuat fungsi lebih mudah dibaca daripada pernyataan singkat, bahkan padat yang menghilangkan pengulangan dan / atau meminimalkan peluang kesalahan.
Contoh saya yang terbaru: Program saya mengambil input, dan karena pedoman format yang kaku, ia dapat dengan mudah menentukan apakah input harus dienkripsi atau didekripsi. Untuk menyederhanakan, setelah kunci enkripsi dan pesan dikonversi / dihasilkan agar kompatibel, itu adalah masalah mengurangi kunci dari pesan terenkripsi atau menambahkan kunci ke pesan yang tidak dienkripsi, untuk mendapatkan output yang diinginkan (anggap kunci sebagai enkripsi, message + enkripsi = kode; kode - enkripsi = pesan). Posisi KERING mengatakan kepada saya bahwa saya harus mengubah pesan terenkripsi saya berbeda dari pesan tidak terenkripsi sehingga fungsi yang mengambil kunci enkripsi dan menerapkannya pada pesan tidak perlu dibedakan. Saya telah menemukan bahwa ini berarti saya perlu beberapa pernyataan bersarang jika fungsi tetapi logika tampaknya solid. Namun, kode ini tidak mudah dibaca.
Saya bisa, di sisi lain, menulis dua fungsi berbeda yang dipanggil berdasarkan flag yang diset ketika aplikasi menentukan enkripsi atau dekripsi. Ini akan lebih mudah dibaca tetapi akan menduplikasi fungsi tingkat tinggi menerapkan kunci enkripsi ke pesan (menyebabkannya dienkripsi atau didekripsi).
Haruskah saya condong ke arah kode yang mudah dibaca, atau kode ringkas? Atau apakah saya melewatkan cara lain untuk mendapatkan fungsi ini dan memenuhi kedua prinsip? Apakah itu posisi sepanjang skala di mana seseorang harus mempertimbangkan tujuan proyek dan membuat keputusan terbaik untuk melayani tujuan itu?
Sejauh ini, saya cenderung menekankan kode DRY yang ringkas dan lebih mudah dibaca.
Jawaban:
KERING adalah pedoman, bukan agama. Mereka yang membawanya ke titik KERING di atas segalanya, telah mengambilnya terlalu jauh.
Pertama dan terpenting, kode yang dapat digunakan adalah yang terpenting. Jika kode tidak berguna dan tidak dapat digunakan, itu tidak ... dan tidak ada gunanya menulisnya di tempat pertama.
Kedua, suatu hari, seseorang harus menjaga kode Anda. Jika kode Anda tidak dapat dipertahankan, mereka akan merusak desain Anda yang padat, ringkas, KERING sambil mengutuk nama Anda. Jangan lakukan ini. Saya telah menjadi orang itu dan setiap kali saya melihat nama tertentu dalam anotasi kode, saya bergidik.
Membuat kode yang padat yang tidak memiliki "variabel deskriptif" dan memasukkan semuanya ke dalam ekspresi ternary bersarang dengan lambdas tanpa dokumentasi apa pun adalah cerdas. Sangat menyenangkan mengetahui bahwa Anda dapat melakukannya - tetapi tidak. Kode pintar sangat sulit untuk di-debug. Hindari menulis kode pintar .
Sebagian besar waktu yang dihabiskan dalam perangkat lunak dihabiskan untuk pemeliharaan perangkat lunak - bukan menulisnya pertama kali. Tulis kode sehingga Anda (atau orang lain) dapat dengan cepat dan mudah memperbaiki bug dan menambahkan fitur yang diperlukan dengan sedikit perubahan desain yang ideal.
sumber
Saya tidak yakin berdasarkan pertanyaan yang Anda mengerti KERING. Kode KERING tidak sama dengan ringkas. Cukup sering justru sebaliknya.
Di sini, saya tidak yakin apa masalahnya untuk contoh ini. Buat fungsi untuk mengenkripsi, fungsi untuk mendekripsi, pembantu fungsi umum (mix bytes), dan front end sederhana untuk mengambil input dan menentukan enkripsi / dekripsi ... Tidak perlu mengulangi sendiri.
Secara umum, baik KERING dan mudah dibaca ada untuk membantu menjaga dan memperluas kode. Tidak semua skenario sama, hit yang mudah dibaca untuk menghapus sedikit pengulangan tidak baik, dan begitu pula banyak duplikasi untuk menambah sedikit keterbacaan.
Jika ditekan, saya lebih suka keterbacaan. Kode duplikat masih dapat diuji - kode yang tidak dapat dibaca mengarah ke Anda melakukan (dan menguji) hal yang salah.
sumber
Saya tidak terbiasa dengan kasus spesifik Anda, tetapi dapat memberikan beberapa panduan umum.
Tujuan dari keterbacaan dan KERING adalah kemampuan pemeliharaan .
Maintainability penting dalam kebanyakan situasi Anda akan menghabiskan lebih banyak waktu mempertahankan kode daripada menulisnya. Ini terutama benar jika Anda menganggap menulis kode sebagai jenis perawatan khusus.
Sayangnya, KERING sering disalahpahami. Ini sebagian karena tampaknya sangat sederhana, tetapi seperti banyak hal sederhana itu bisa, yah ... rumit.
Tujuannya KERING adalah bahwa setiap unit fungsi hanya ada di satu tempat. Jika prinsip ini diikuti, pengelola kode yang ditugaskan untuk mengubah atau memverifikasi fungsionalitas dapat menangani kode sekaligus. Jika KERING tidak diikuti maka ada bahaya yang sangat nyata bahwa beberapa salinan fungsi tidak akan dikelola dengan baik.
Pelanggaran DRY yang paling mencolok adalah copy-paste coding, di mana seluruh blok kode diulang-ulang dalam basis kode. Ini secara mengejutkan umum dalam pengalaman saya, dan tidak ada cara yang menambah keterbacaan. Oleh karena itu, refactoring kode untuk memperkenalkan metode umum selalu meningkatkan kesesuaian dan keterbacaan KERING.
Pelanggaran kedua yang paling mencolok adalah "salin dan tempel sedikit". Sekali lagi, refactoriing untuk memperkenalkan metode umum dengan parameter, atau memecah fungsi menjadi langkah-langkah dan mengabstraksi kesamaan hampir selalu meningkatkan keterbacaan.
Lalu ada pelanggaran yang lebih halus, di mana fungsionalitas digandakan tetapi kodenya berbeda. Ini selalu tidak mudah dikenali, tetapi ketika Anda melihatnya dan refactor untuk menarik kode umum ke dalam satu metode / kelas / fungsi maka kode tersebut secara umum lebih mudah dibaca daripada sebelumnya.
Akhirnya, ada kasus pengulangan desain. Misalnya, Anda mungkin telah menggunakan pola keadaan beberapa kali dalam basis kode Anda, dan Anda sedang mempertimbangkan refactoring untuk menghilangkan pengulangan ini. Dalam hal ini, lanjutkan dengan hati-hati. Anda mungkin mengurangi keterbacaan dengan memperkenalkan lebih banyak level abstraksi. Pada saat yang sama, Anda tidak benar-benar berurusan dengan duplikasi fungsi tetapi dengan duplikasi abstraksi. Terkadang itu sepadan ... tetapi seringkali tidak. Prinsip panduan Anda adalah bertanya, "yang mana yang lebih bisa dipertahankan".
Setiap kali saya membuat panggilan penilaian ini, saya mencoba mempertimbangkan jumlah waktu yang dihabiskan orang untuk mempertahankan kode. Jika kode adalah fungsionalitas inti bisnis maka mungkin perlu lebih banyak pemeliharaan. Dalam hal ini saya bertujuan untuk membuat kode dapat dikelola untuk orang-orang yang akrab dengan basis kode dan abstraksi yang terlibat. Saya akan lebih senang memperkenalkan sedikit abstraksi untuk mengurangi pengulangan. Sebaliknya, naskah yang jarang digunakan dan jarang dipelihara mungkin kurang mudah dipahami oleh pengelola jika melibatkan terlalu banyak abstraksi. Dalam hal ini saya akan melakukan kesalahan di sisi pengulangan.
Saya juga mempertimbangkan tingkat pengalaman anggota tim saya yang lain. Saya menghindari abstraksi "mewah" dengan pengembang yang tidak berpengalaman, tetapi memanfaatkan pola desain yang diakui industri dengan kelompok yang lebih matang.
Dalam kesimpulan, jawaban atas pertanyaan Anda adalah melakukan apa pun yang membuat kode Anda paling bisa dipertahankan. Apa artinya itu dalam skenario Anda tergantung pada Anda untuk memutuskan.
sumber
Jika fungsi Anda menjadi lebih rumit dan lebih lama (sehingga kurang dapat dibaca) ketika Anda mencoba membuatnya KERING, maka Anda salah melakukannya. Anda mencoba untuk menempatkan terlalu banyak fungsi dalam satu fungsi karena Anda berpikir bahwa ini adalah satu-satunya cara untuk menghindari mengulangi potongan kode yang sama dalam fungsi kedua.
Membuat kode KERING hampir selalu berarti mengembalikan fungsi umum ke fungsi yang lebih kecil. Masing-masing fungsi itu harus lebih sederhana (dan dengan demikian lebih mudah dibaca) daripada yang asli. Untuk menjaga segala sesuatu dalam fungsi asli pada tingkat abstraksi yang sama, ini juga dapat berarti untuk memperbaiki bagian tambahan yang tidak digunakan di tempat lain. Fungsi asli Anda kemudian menjadi "fungsi tingkat tinggi", memanggil yang lebih kecil, dan menjadi lebih kecil dan lebih sederhana juga.
Dengan melakukan hal ini, sebagian besar mengarah ke berbagai level abstraksi dalam kode Anda - dan beberapa orang percaya kode semacam itu kurang dapat dibaca. Menurut pengalaman saya, ini adalah kekeliruan. Poin kunci di sini adalah untuk memberi fungsi yang lebih kecil nama yang baik, memperkenalkan tipe data yang bagus dan abstraksi yang dapat dengan mudah dipahami oleh orang kedua. Dengan cara itu "KERING" dan "keterbacaan" seharusnya hanya sangat, sangat jarang menimbulkan konflik.
sumber
Meskipun saya tidak yakin persis apa yang menyebabkan masalah di sini, pengalaman saya adalah ketika Anda menemukan KERING dan keterbacaan yang bertentangan yang mengatakan ini saatnya untuk memperbaiki sesuatu.
sumber
Saya akan memilih yang dapat dibaca (= dapat dipelihara) daripada KERING setiap hari dalam seminggu. Pada kenyataannya keduanya sering disejajarkan, seseorang yang mendapat konsep KERING umumnya akan menghasilkan (kebanyakan) kode yang dapat dibaca.
sumber
Sangat sangat sangat sangat sangat sedikit dalam karir saya, saya menemukan kasus yang sah bahwa pitt mudah dibaca terhadap KERING. Jadikan itu mudah dibaca dulu. Sebutkan hal-hal dengan baik. Salin dan tempel jika perlu.
Sekarang mundur dan lihat totalitas yang telah Anda buat, seperti seorang seniman melangkah mundur untuk melihat lukisan mereka. Sekarang Anda dapat mengidentifikasi pengulangan dengan benar.
Kode yang berulang harus di refactored ke dalam metodenya sendiri, atau ditarik keluar ke kelasnya sendiri.
Kode berulang harus menjadi pilihan terakhir. Dapat dibaca DAN KERING terlebih dahulu, gagal terbaca jika Anda membatasi ruang lingkup kode berulang.
sumber