Mengapa "salin dan tempel" kode berbahaya? [Tutup]


130

Terkadang, bos saya akan mengeluh kepada kami:

Mengapa kita perlu waktu yang lama untuk mengimplementasikan fitur?

Sebenarnya, fitur tersebut telah diterapkan di aplikasi lain sebelumnya, Anda hanya perlu menyalin dan menempelkan kode dari sana. Biaya harus rendah.

Ini benar-benar pertanyaan yang sulit, karena menyalin dan menempelkan kode bukanlah hal yang sederhana dalam pandangan saya.

Apakah Anda punya alasan bagus untuk menjelaskan hal ini kepada atasan non-teknis Anda?


19
itu semacam suara daripada menyalin dan menempelkan kode dari aplikasi Anda sebelumnya ke yang baru, Anda menulis ulang fungsi yang sama lagi dan lagi. Saya pikir prinsip KERING diarahkan lebih ke arah tidak memiliki fungsi yang sama digandakan di seluruh sistem, tetapi menggunakan kembali kode dari aplikasi lain lebih baik daripada menulis ulang itu.
Carson Myers

5
Karena setiap kali Anda menyalin dan menempelkan kode, segel bayi terbunuh.
DeadlyChambers

@CarsonMyers Hanya jika komponen dapat digunakan kembali. Dan itu dimaksudkan agar sesuai dengan konteks saat ini.
Sreekanth Karumanaghat

Jawaban:


171

Jika Anda menemukan bug dalam kode salin-tempel, Anda harus memperbaikinya di setiap tempat yang Anda lakukan dan berharap Anda dapat mengingat semuanya (ini juga berlaku untuk persyaratan yang diubah).

Jika Anda menyimpan logika di satu tempat, lebih mudah untuk mengubah saat diperlukan (jadi jika Anda memutuskan bahwa aplikasi perlu diperbarui, Anda hanya melakukannya di satu tempat).

Mintalah atasan Anda membaca tentang prinsip KERING (Jangan Ulangi Diri Sendiri).

Apa yang Anda gambarkan terdengar seperti penggunaan yang sempurna untuk perpustakaan , tempat Anda membagikan kode dan hanya menyimpannya di satu tempat.

Saya akan hanya pernah copy-paste kode jika saya dimaksudkan untuk refactor segera setelah - memastikan aku nanti kode umum diekstraksi sehingga saya bisa menggunakan kembali sebanyak logika mungkin. Dan segera setelah itu, maksud saya beberapa menit kemudian, bukan hari dan minggu.


41
+1. Intinya adalah bahwa salin dan tempel murah untuk menyelesaikan masalah langsung. Masalah sebenarnya adalah bahwa dalam jangka menengah / panjang biaya untuk mempertahankan kode duplikat jauh lebih tinggi daripada kode yang difaktorkan dengan baik
Paolo

7
Ini bukan hanya masalah bug; persyaratan program dapat berubah. Saya telah mengubah empat dari lima tempat di mana sesuatu perlu diubah sebelumnya.
David Thornley

1
Jika Anda dapat menyalin-n-tempel saat diminta, dan melacak di mana duplikat itu mudah di-abstraksi atau diperbarui, maka salin dan tempel bukanlah hal yang buruk untuk dilakukan. Lihat diskusi tentang pendeteksian klon di www.semanticdesigns.com/Products/Clone untuk perincian lebih lanjut dan untuk alat-alat yang dapat dilakukan.
Ira Baxter

4
Banyak di ifssana, dan sebagian besar alat tidak mendukung deteksi kloning pada saat ini.
Oded

2
Alkisah ada seorang programmer yang bekerja untuk ESA . Dia sedang mengerjakan perangkat lunak untuk roket Ariane-5 dan dia menggunakan metode salin-tempel. Kemudian s ... terjadi
Hauleth

25

Anda akan jauh lebih baik berbagi kode dengan membangun perpustakaan daripada menyalin kode menggunakan salin dan tempel.

Anda masih akan mendapatkan keuntungan kecepatan daripada menulis ulang (mencari KERING) tetapi hanya akan memiliki satu tempat untuk mempertahankan kode.


1
Saya hanya ingin tahu, mengapa Anda "memotong" kode jika yang perlu Anda lakukan adalah menduplikasinya?
dpp

Poin bagus dpp. Diedit!
CResults

12

Alasan yang jelas adalah bahwa Anda mengambil 'hutang' untuk masa depan: setiap perubahan yang perlu Anda lakukan dalam kode (bukan hanya perbaikan bug, perubahan apa pun) sekarang akan dua kali lebih mahal untuk dilakukan karena Anda harus memperbarui dua tempat - dan lebih berisiko karena Anda AKAN akan melupakan salah satu dari mereka pada akhirnya. Dengan kata lain, menjadikannya bekerja lebih cepat sekarang akan membuat pekerjaan Anda lebih lambat di masa depan, yang bisa menjadi akal bisnis yang baik tetapi biasanya tidak.

Tetapi alasan yang lebih penting adalah bahwa asumsi "ini sama dengan itu" lebih sering salah. Setiap kali kode Anda bergantung pada asumsi yang tidak diucapkan untuk menjadi benar, menyalinnya ke tempat lain menghasilkan kesalahan kecuali asumsi ini juga berlaku di tempat baru. Oleh karena itu, kode yang disisipkan sering salah sejak awal dan tidak hanya setelah perubahan berikutnya.


11

Desain-bijaksana, copy-paste kode tentu saja merupakan bencana, dengan potensi untuk menyebabkan banyak masalah di masa depan. Tetapi Anda bertanya mengapa ini membutuhkan banyak pekerjaan saat ini , jawabannya adalah: karena tidak pernah hanya menyalin dan menempel.

Jika kode asli ditulis untuk digunakan kembali, sebagai perpustakaan yang cukup independen, dengan fleksibilitas dan penggunaan klien dalam pikiran - bagus, tapi itu bukan copy-paste, itu menggunakan perpustakaan kode. Copy-paste kode sebenarnya biasanya lebih seperti ini:

  • "Tentu, aku sudah punya kode yang melakukan itu!"
  • "Tunggu, yang mana dari lima versi kode ini yang ingin aku gunakan sebagai sumberku?"
  • "Hmmm, apa fungsi semua fungsi 'util_func_023' ini? Bukankah aku mendokumentasikannya? Manakah dari mereka yang aku butuhkan sekarang?"
  • "Oh, ya, kode ini menggunakan Basis Kode Y. Kira saya perlu [ memilih satu: salin semua Basis Kode Y ke proyek baru saya / menghabiskan satu hari melepaskan satu fungsi yang saya inginkan dari Basis Kode Y / menghabiskan waktu seminggu melepaskan satu fungsi yang saya inginkan dari Code Base Y]. "
  • "Aku menyalin semuanya, yay!"
  • "Kenapa ini tidak berhasil?"
  • Ini adalah titik di mana Anda menghabiskan berjam-jam / hari / minggu men-debug kode yang ada yang mirip dengan yang Anda inginkan, alih-alih menulis kode yang sebenarnya ingin Anda mulai.

Singkatnya, kode yang ada yang tidak dapat digunakan secara langsung, paling tidak, dapat berfungsi sebagai referensi yang baik untuk menulis kode yang sama. Ini tentu saja tidak dapat diangkat seluruhnya dan diharapkan bekerja dalam sistem yang sama sekali berbeda. Secara umum, ini adalah asumsi yang aman bahwa kode apa pun yang telah ditulis dan diselesaikan, harus dikacaukan sesedikit mungkin - bahkan ketika itu adalah salinan dan bukan yang asli itu sendiri.

Jika Anda ingin mendasarkan proyek Anda pada copy-paste, Anda harus memulai kode dengan cara yang memungkinkan penggunaan kembali yang mudah, tanpa menyalin kode asli itu dan mengacaukannya. Itu layak dilakukan, dan jika itu yang diharapkan bos Anda, maka Anda berdua perlu memastikan bahwa itulah cara Anda merancang dan bekerja.


9

copy dan paste adalah bencana yang menunggu untuk terjadi. Bos Anda harus mengevaluasi harga pengiriman lebih awal sehubungan dengan harga kode yang rusak dikirimkan ke pengguna akhir segera.


9

Jika Anda sudah menerapkan fitur dan Anda perlu menyalin dan menempel untuk menggunakannya kembali, sepertinya Anda telah melakukan sesuatu yang salah. Tidak bisakah Anda meletakkan fitur-fitur ini di perpustakaan sehingga Anda dapat menggunakannya kembali tanpa menyalin / menempel?


8

Prinsip KERING (Don't Repeat Yourself): KERING di wikipedia .

"Setiap pengetahuan harus memiliki representasi tunggal, tidak ambigu, otoritatif dalam suatu sistem."

tautan lainnya .


Ini seperti mengatakan, "jangan pernah menusukkan pisau ke tenggorokan pria", yang terdengar seperti aturan yang sangat baik. Sampai Anda menyadari bahwa dokter HARUS melanggar aturan ini untuk melakukan trachiotomy untuk menyelamatkan nyawa pria (jika dia tidak bisa bernapas, mungkin karena anafilaksis, reaksi alergi yang ekstrem). Setiap aturan memiliki pengecualian (kecuali, mungkin, untuk yang satu ini - bahwa setiap aturan memiliki pengecualian). Oleh karena itu, setiap aturan harus memiliki alasan dan kapan serta daftar pengecualian, semuanya terlampir, untuk realitas "rekayasa" yang sebenarnya, yang jawabannya adalah tergantung pada ...
MicroservicesOnDDD

Jadi ... kapan kamu TIDAK mengikuti KERING? Saya terus-menerus bergumul dengan ini di pekerjaan saya saat ini, yang ada hubungannya dengan firmware, dan jawabannya adalah bahwa kita "membuka gulungan" dan melakukan hal-hal lain karena itu "meningkatkan kinerja." Kami memiliki hierarki pewarisan yang sangat dangkal, dan kami menggunakan sebagian besar kelas secara langsung alih-alih mensubklasifikasikan mereka, dan ... ... kami banyak menggunakan salin dan rekat. Dan saya membencinya, karena itu membuat basis kode kami lebih sulit untuk dipahami dan lebih sulit untuk dipelihara. Tapi kami punya alasan, dan itu alasan yang bisa diterima. Kami bukan satu-satunya pemangku kepentingan. Dan menemukan keseimbangan yang tepat lebih merupakan seni.
MicroservicesOnDDD

7

Kedengarannya bagi saya seperti kesalahpahaman terburuk yang dimiliki bos non-teknis Anda, adalah pekerjaan Anda yang paling banyak mengetik. Mereka pikir Anda dapat menghemat banyak waktu dengan menghilangkan pengetikan.

Saya pikir pendidikan terbaik yang bisa Anda berikan kepada orang ini adalah untuk menunjukkan semua pekerjaan yang Anda lakukan yang tidak diketik. Bahkan jika sebagian besar pekerjaan itu biasanya terjadi secara tak terlihat, di kepala Anda, bersamaan dengan mengetik.

Tentu, menghilangkan pengetikan akan menghemat waktu. Tetapi kemudian bagian pekerjaan Anda yang jauh lebih besar, tidak mengetik, menjadi lebih besar dan memakan waktu hemat dan lebih banyak lagi.


4

Apakah Anda yakin bos Anda ingin mendengar tentang prinsip KERING, bug, dan hal-hal teknologi lainnya?

Komentar seperti itu biasanya Anda dengar ketika bos atau perusahaan Anda meremehkan waktu yang dibutuhkan untuk menyelesaikan beberapa proyek. Dan berdasarkan estimasi yang salah kontrak ditandatangani, dll. Dalam kebanyakan kasus, programmer tidak terlibat dalam estimasi.

Kenapa ini terjadi? Terkadang sponsor proyek memiliki anggaran terlalu kecil. Mungkin proses bisnis Anda mengotomatisasi menggunakan perangkat lunak tidak sepadan dengan upaya tim Anda. Manajer umumnya cenderung sangat tertutup untuk berita buruk dalam kasus seperti itu. Di awal proyek ada angan-angan. Kemudian manajer mencoba menyalahkan programmer. Dalam kasus Anda secara tidak langsung melalui salin dan tempel. Dalam kasus ekstrim ini disebut pawai kematian .


3

Menyalin dan menempelkan kode biasanya mengarah ke Pemrograman karena Kebetulan


Saya menemukan artikel ini ditulis dengan sangat buruk. Narasi tetap abstrak sehingga gagal menjelaskan kasus di luar fakta bahwa Fred bekerja secara iteratif. Satu masalah yang jelas dimiliki Fred adalah bahwa ia tidak memiliki gagasan bagus tentang keseluruhan arsitektur. Sayangnya, ini sangat sering terjadi ketika kita bekerja dengan kode warisan yang tidak berdokumen di mana pengetahuannya hilang. Referensi Desain oleh Kontrak dan Pemrograman Asertif cukup baik, tetapi sayangnya bahkan setelah mereka contoh / latihan dibiarkan tidak dijelaskan.
mapto

3

Saya pikir " aplikasi lain " adalah kunci di sini, jika aplikasi lain sudah diuji dan sedang digunakan, itu tidak boleh diubah untuk menggunakan perpustakaan umum, karena itu Anda tidak dapat berbagi kode dengannya.

Dalam aplikasi yang sama , "salin dan tempel" buruk, tetapi antara basis kode yang dikembangkan oleh tim yang berbeda atau dengan siklus rilis yang berbeda, "salin dan tempel" dapat menjadi pilihan terbaik.


Meskipun saya dapat melihat bahwa tidak ada gunanya merilis pembaruan ke aplikasi lain hanya untuk menggunakan pustaka, mungkin ide yang baik untuk setidaknya membuat perubahan pada cabang fitur yang diperlukan. Ini akan memberi Anda rasa percaya diri bahwa antarmuka perpustakaan cukup umum untuk setidaknya dua aplikasi yang bersangkutan, dan memungkinkan Anda untuk menggabungkan perubahan pada titik yang tepat dalam siklus rilis.
SamB

2

Saya bekerja untuk perusahaan serupa. Menjadi trainee, saya tidak tahu lebih baik, jadi ketika saya memulai proyek baru, bos saya juga menyarankan untuk menempelkan kode dari tempat lain. Yah, seperti yang mungkin Anda pikirkan, seluruh perangkat lunak itu cukup berantakan, sampai-sampai ketika Anda mencoba untuk memperbaiki bug, dua bug baru muncul.


2

Bahkan jika aplikasi lain sudah memiliki fitur yang Anda butuhkan, kode untuk fitur itu mungkin tidak cocok dengan aplikasi Anda saat ini tanpa penulisan ulang utama. Ini seperti mengambil motor Ford dan mencoba memasangnya menjadi Toyota. Secara umum, ada aturan praktis bahwa jika Anda harus memodifikasi lebih dari 25% dari kode yang Anda salin, lebih baik (lebih murah) untuk menulis ulang dari awal.

Mengekstraksi kode yang dipertanyakan ke dalam perpustakaan terdengar menarik, tetapi mungkin lebih sulit daripada kedengarannya, tergantung pada bagaimana sistem lain dibangun. Misalnya kode untuk fitur itu mungkin sulit untuk diekstraksi karena ia menghubungkan banyak kode lain dengan cara yang tidak jelas (misalnya dengan mengakses banyak variabel global, dll.)


1

Katakan kepada atasan Anda bahwa bagian dari masing-masing dan setiap nama variabel termasuk nama proyek lama dan sekarang Anda harus mengubah semuanya, secara manual. Jika bos Anda tidak tahu (atau ingin tahu) mengapa copy / paste itu buruk, ia mungkin juga percaya itu :)


1

Ya, masalah terbesar adalah bahwa itu bukan hanya salin dan tempel - salinnya lalu tempel kemudian sedikit modifikasi.

Kemudian di kemudian hari ketika salah satu varian yang disisipkan memiliki masalah, itu akan berubah. Kemudian, varian lain berubah.

Kemudian, Anda mengetahui bahwa semua varian harus berubah karena salinan asli memiliki bug. Sekarang Anda baik-baik saja dan benar-benar kacau karena semua area yang disisipkan sekarang tidak sama.

Dan tidakkah Anda mengetahuinya, pengkodean jelek seperti ini biasanya hampir seluruhnya kosong dari komentar.

Bagi saya, perbedaannya adalah ketika Anda memiliki banyak salinan kode melakukan hal yang sama, apa yang Anda miliki adalah banyak kode. Ketika Anda hanya memiliki satu kode yang melakukan setiap hal tertentu, maka Anda memiliki sistem.

Perilaku suatu sistem dapat diubah dengan modifikasi titik tunggal dengan cukup mudah - mengubah perilaku sekelompok kode memerlukan banyak kode.

Saya suka sistem, bukan banyak kode.


1

Ada trade-off antara kecepatan pengembangan fungsi langsung di depan Anda (terutama ketika aplikasi kecil), dan biaya pemeliharaan jangka panjang seiring aplikasi tumbuh.

Menyalin dan menempel lebih cepat untuk fungsionalitas langsung, tetapi akan membebani Anda dengan biaya saat ukuran aplikasi bertambah, dalam hal memperbaiki bug dan membuat perubahan sistem yang luas dan mempertahankan alur kerja di antara berbagai komponen aplikasi.

Itulah argumen yang perlu didengar pemilik bisnis. Ini mirip dengan biaya yang diterima untuk memelihara armada kendaraan, namun, dengan perangkat lunak, aspek arsitektur perangkat lunak yang rusak umumnya tersembunyi di sisi bisnis, dan hanya dapat dilihat oleh pengembang.


0

Dia benar bahwa jika tim telah menerapkan fungsi serupa sebelumnya, mengulanginya akan jauh lebih mudah pada kali ke-2.

Namun, Anda mungkin harus menjelaskan bahwa setiap aplikasi berbeda. Hanya karena Anda memasang pintu di satu rumah tidak berarti Anda dapat memasang pintu lain di rumah lain dalam waktu singkat - Anda akan lebih cepat karena pengalaman (# pintu terpasang), tetapi masih membutuhkan waktu untuk mendapatkan peralatan Anda , pasang pintu, pastikan pintu sudah terpasang, dan pasang ke dalam bingkai.


0

di perusahaan saya, kami selalu bekerja dengan kelas dan metode, dan membuat dokumentasi teknis untuk mereka. Saya pikir ini praktik terbaik jika Anda dapat menggunakan aplikasi pencarian svn Anda sendiri dengan kunci yang baik untuk menemukan kelas metode yang digunakan sebelumnya :)

Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.