Kita semua yang bekerja dengan database relasional telah belajar (atau sedang belajar) bahwa SQL berbeda. Menggali hasil yang diinginkan, dan melakukannya dengan efisien, melibatkan proses yang membosankan yang sebagian ditandai dengan mempelajari paradigma yang tidak dikenal, dan menemukan bahwa beberapa pola pemrograman kita yang paling dikenal tidak bekerja di sini. Apa antipatterns umum yang Anda lihat (atau diri Anda berkomitmen)?
sql
anti-patterns
le dorfier
sumber
sumber
Jawaban:
Saya secara konsisten kecewa dengan kecenderungan kebanyakan programmer untuk mencampurkan logika UI mereka di lapisan akses data:
Biasanya, programmer melakukan ini karena mereka berniat untuk mengikat dataset mereka langsung ke grid, dan itu hanya nyaman untuk memiliki format SQL Server sisi server daripada format pada klien.
Query seperti yang ditunjukkan di atas sangat rapuh karena mereka memadatkan layer data dengan layer UI. Selain itu, gaya pemrograman ini secara menyeluruh mencegah prosedur tersimpan tidak dapat digunakan kembali.
sumber
Inilah 3 teratas saya.
Nomor 1. Gagal menentukan daftar bidang. (Sunting: untuk mencegah kebingungan: ini adalah aturan kode produksi. Ini tidak berlaku untuk skrip analisis satu kali - kecuali saya penulisnya.)
seharusnya
Nomor 2. Menggunakan kursor dan loop sementara, ketika loop sementara dengan variabel loop akan dilakukan.
Nomor 3. DateLogic melalui tipe string.
Seharusnya
Saya telah melihat lonjakan baru-baru ini "Satu permintaan lebih baik dari dua, oke?"
Permintaan ini membutuhkan dua atau tiga rencana eksekusi yang berbeda tergantung pada nilai parameter. Hanya satu paket eksekusi yang dihasilkan dan dimasukkan ke cache untuk teks sql ini. Paket itu akan digunakan terlepas dari nilai parameter. Ini berakibat pada kinerja buruk yang terputus-putus. Jauh lebih baik untuk menulis dua kueri (satu permintaan per rencana eksekusi yang dimaksudkan).
sumber
Bidang kata sandi yang dapat dibaca manusia , egad. Cukup jelas.
Menggunakan LIKE terhadap kolom yang diindeks , dan saya hampir tergoda untuk mengatakan LIKE secara umum.
Daur ulang nilai-nilai PK yang dihasilkan SQL.
Tidak ada yang mengejutkan menyebutkan meja dewa . Tidak ada yang mengatakan "organik" seperti 100 kolom bendera bit, string besar dan bilangan bulat.
Lalu ada pola "I miss .ini file" : menyimpan CSV, string yang dibatasi pipa, atau data parse lain yang diperlukan dalam bidang teks besar.
Dan untuk MS SQL server penggunaan kursor sama sekali . Ada cara yang lebih baik untuk melakukan tugas kursor apa pun.
Diedit karena ada begitu banyak!
sumber
LIKE '%LIKE'
.Tidak harus menggali lebih dalam untuk itu: Tidak menggunakan pernyataan yang disiapkan.
sumber
Menggunakan alias tabel yang tidak berarti:
Membuat membaca pernyataan SQL besar jauh lebih sulit daripada yang seharusnya
sumber
sumber
Bugbears saya adalah tabel Akses kolom 450 yang telah disatukan oleh putra berusia 8 tahun dari sahabat anjing groomer Direktur Pelaksana dan tabel pencarian cerdik yang hanya ada karena seseorang tidak tahu bagaimana menormalkan struktur data dengan benar.
Biasanya, tabel pencarian ini terlihat seperti ini:
Saya telah kehilangan hitungan jumlah klien yang pernah saya lihat yang memiliki sistem yang mengandalkan kekejian seperti ini.
sumber
Yang paling saya sukai adalah
Menggunakan spasi saat membuat tabel, sprocs dll. Saya baik-baik saja dengan CamelCase atau under_scores dan tunggal atau bentuk jamak dan huruf besar atau huruf kecil tetapi harus merujuk ke tabel atau kolom [dengan spasi], terutama jika [spasi aneh] (ya, Saya mengalami ini) benar-benar membuat saya jengkel.
Data yang dinormalisasi. Sebuah tabel tidak harus dinormalisasi secara sempurna, tetapi ketika saya bertemu dengan tabel karyawan yang memiliki informasi tentang skor evaluasi mereka saat ini atau apa pun yang utama, itu memberi tahu saya bahwa saya mungkin perlu membuat tabel terpisah di beberapa titik dan kemudian coba sinkronkan. Saya akan menormalkan data terlebih dahulu dan kemudian jika saya melihat tempat di mana denasionalisasi membantu, saya akan mempertimbangkannya.
Terlalu sering menggunakan pandangan atau kursor. Tampilan memiliki tujuan, tetapi ketika setiap tabel dibungkus dalam tampilan itu terlalu banyak. Saya harus menggunakan kursor beberapa kali, tetapi secara umum Anda dapat menggunakan mekanisme lain untuk ini.
Mengakses. Bisakah suatu program menjadi anti-pola? Kami memiliki SQL Server di tempat kerja saya, tetapi sejumlah orang menggunakan akses karena ketersediaannya, "kemudahan penggunaan" dan "keramahan" untuk pengguna non-teknis. Ada terlalu banyak di sini untuk dituju, tetapi jika Anda berada di lingkungan yang sama, Anda tahu.
sumber
gunakan SP sebagai awalan dari nama prosedur toko karena ia akan mencari lebih dulu di lokasi prosedur sistem daripada yang kustom.
sumber
Terlalu sering menggunakan meja sementara dan kursor.
sumber
Untuk menyimpan nilai waktu, hanya zona waktu UTC yang harus digunakan. Waktu setempat tidak boleh digunakan.
sumber
menggunakan @@ IDENTITY alih-alih SCOPE_IDENTITY ()
Dikutip dari jawaban ini :
sumber
Menggunakan kembali bidang 'mati' untuk sesuatu yang tidak dimaksudkan (misalnya menyimpan data pengguna dalam bidang 'Faks') - sangat menggoda sebagai perbaikan cepat!
sumber
dan dengan asumsi bahwa hasilnya akan diurutkan berdasarkan some_column. Saya telah melihat ini sedikit dengan Sybase di mana asumsi itu berlaku (untuk saat ini).
sumber
Atau, menjejalkan semuanya menjadi satu baris.
sumber
The
FROM TableA, TableB WHERE
sintaks untuk BERGABUNG daripadaFROM TableA INNER JOIN TableB ON
Membuat asumsi bahwa permintaan akan dikembalikan disortir dengan cara tertentu tanpa memasukkan klausa ORDER BY, hanya karena itulah yang muncul selama pengujian di alat kueri.
sumber
Belajar SQL dalam enam bulan pertama karir mereka dan tidak pernah belajar hal lain selama 10 tahun ke depan. Khususnya tidak belajar atau secara efektif menggunakan fitur windowing / analitik SQL. Khususnya penggunaan over () dan partisi oleh.
Lihat O'Reilly SQL Cookbook Lampiran A untuk tinjauan umum yang bagus dari fungsi windowing.
sumber
Saya perlu menempatkan favorit saya saat ini di sini, hanya untuk membuat daftar lengkap. Antipattern favorit saya tidak menguji kueri Anda .
Ini berlaku ketika:
Dan setiap tes dijalankan terhadap data atipikal atau tidak mencukupi tidak masuk hitungan. Jika ini adalah prosedur yang tersimpan, masukkan pernyataan tes ke dalam komentar dan simpan, dengan hasilnya. Kalau tidak, masukkan ke dalam komentar dengan kode hasilnya.
sumber
Penyalahgunaan Tabel Sementara.
Khususnya hal semacam ini:
Jangan membangun tabel sementara dari kueri, hanya untuk menghapus baris yang tidak Anda butuhkan.
Dan ya, saya telah melihat halaman kode dalam bentuk ini di DB produksi.
sumber
Pandangan pelawan: obsesi berlebihan dengan normalisasi.
Sebagian besar sistem SQL / RBDBs memberikan satu banyak fitur (transaksi, replikasi) yang cukup berguna, bahkan dengan data yang tidak diformalkan. Ruang disk murah, dan kadang-kadang bisa lebih sederhana (kode lebih mudah, waktu pengembangan lebih cepat) untuk memanipulasi / memfilter / mencari data yang diambil, daripada menulis skema 1NF, dan menangani semua kerepotan di dalamnya (gabungan yang kompleks, sub-pilihan yang tidak menyenangkan) , dll).
Saya telah menemukan bahwa sistem yang terlalu dinormalisasi seringkali merupakan optimasi prematur, terutama pada tahap pengembangan awal.
(lebih banyak pemikiran tentang itu ... http://writeonly.wordpress.com/2008/12/05/simple-object-db-using-json-and-python-sqlite/ )
sumber
Saya hanya menyatukan ini, berdasarkan pada beberapa respons SQL di sini pada SO.
Ini adalah antipattern yang serius untuk berpikir bahwa pemicu adalah untuk database seperti event handler ke OOP. Ada persepsi bahwa sembarang logika lama dapat dimasukkan ke dalam pemicu, untuk dipecat ketika transaksi (peristiwa) terjadi di atas meja.
Tidak benar. Salah satu perbedaan besar adalah bahwa pemicu sinkron - dengan balas dendam, karena mereka sinkron pada operasi yang ditetapkan, bukan pada operasi baris. Di sisi OOP, justru sebaliknya - peristiwa adalah cara yang efisien untuk menerapkan transaksi asinkron.
sumber
Prosedur atau Fungsi Tersimpan tanpa komentar ...
sumber
1) Saya tidak tahu ini anti-pola "resmi", tapi saya tidak suka dan mencoba untuk menghindari string literal sebagai nilai ajaib dalam kolom database.
Contoh dari tabel 'gambar' MediaWiki:
(Saya hanya melihat casing yang berbeda, hal lain yang harus dihindari)
Saya merancang kasus-kasus seperti pencarian int ke dalam tabel ImageMediaType dan ImageMajorMime dengan kunci primer int.
2) konversi tanggal / string yang bergantung pada pengaturan NLS tertentu
tanpa pengidentifikasi format
sumber
Subquery identik dalam kueri.
sumber
Tampilan yang Diubah - Tampilan yang terlalu sering diubah dan tanpa pemberitahuan atau alasan. Perubahan akan diketahui pada waktu yang paling tidak tepat atau lebih buruk salah dan tidak pernah diperhatikan. Mungkin aplikasi Anda akan rusak karena seseorang memikirkan nama yang lebih baik untuk kolom itu. Sebagai aturan, pandangan harus memperluas kegunaan tabel dasar sambil mempertahankan kontrak dengan konsumen. Perbaiki masalah tetapi jangan menambahkan fitur atau mengubah perilaku yang lebih buruk, untuk itu buat tampilan baru. Untuk mengurangi jangan berbagi pandangan dengan proyek lain dan, gunakan CTE ketika platform memungkinkan. Jika toko Anda memiliki DBA, Anda mungkin tidak dapat mengubah tampilan tetapi semua tampilan Anda akan usang dan atau tidak berguna dalam hal ini.
The! Paramed - Dapatkan kueri memiliki lebih dari satu tujuan? Mungkin tetapi orang berikutnya yang membacanya tidak akan tahu sampai meditasi mendalam. Bahkan jika Anda tidak membutuhkannya sekarang kemungkinan Anda akan, bahkan jika itu "hanya" untuk debug. Menambahkan parameter menurunkan waktu perawatan dan menjaga keadaan tetap KERING. Jika Anda memiliki klausa di mana Anda harus memiliki parameter.
Kasing tanpa KASUS -
sumber
Dua yang paling saya temukan, dan dapat memiliki biaya yang signifikan dalam hal kinerja adalah:
Menggunakan kursor alih-alih ekspresi berbasis set. Saya kira ini sering terjadi ketika programmer berpikir secara prosedural.
Menggunakan sub-kueri terkait, saat bergabung ke tabel turunan dapat melakukan pekerjaan.
sumber
Menempatkan barang di tabel sementara, terutama orang yang beralih dari SQL Server ke Oracle memiliki kebiasaan menggunakan tabel sementara secara berlebihan. Cukup gunakan pernyataan pilih bersarang.
sumber
Pengembang yang menulis kueri tanpa memiliki ide bagus tentang apa yang membuat aplikasi SQL (baik permintaan individu dan sistem multi-pengguna) cepat atau lambat. Ini termasuk ketidaktahuan tentang:
sumber
Menggunakan SQL sebagai paket ISAM (Indexed Sequential Access Method) yang dimuliakan. Secara khusus, kursor bersarang alih-alih menggabungkan pernyataan SQL menjadi pernyataan tunggal, meskipun lebih besar. Ini juga dianggap sebagai 'penyalahgunaan pengoptimal' karena sebenarnya tidak banyak yang dapat dilakukan pengoptimal. Ini dapat dikombinasikan dengan pernyataan yang tidak disiapkan untuk inefisiensi maksimum:
Solusi yang benar (hampir selalu) adalah menggabungkan dua pernyataan SELECT menjadi satu:
Satu-satunya keuntungan untuk versi loop ganda adalah bahwa Anda dapat dengan mudah melihat jeda antara nilai-nilai dalam Table1 karena loop dalam berakhir. Ini bisa menjadi faktor dalam laporan break-control.
Selain itu, pengurutan dalam aplikasi biasanya tidak boleh.
sumber
Menggunakan kunci utama sebagai pengganti untuk alamat rekaman dan menggunakan kunci asing sebagai pengganti untuk pointer yang tertanam dalam catatan.
sumber