Apa praktik terbaik untuk kunci utama dalam tabel?


256

Saat mendesain tabel, saya telah mengembangkan kebiasaan memiliki satu kolom yang unik dan saya membuat kunci utama. Ini dicapai dalam tiga cara tergantung pada persyaratan:

  1. Kolom bilangan bulat identitas yang bertambah secara otomatis.
  2. Pengidentifikasi unik (GUID)
  3. Kolom karakter pendek (x) atau bilangan bulat (atau tipe numerik lainnya yang relatif kecil) yang dapat berfungsi sebagai kolom pengidentifikasi baris

Angka 3 akan digunakan untuk pencarian yang cukup kecil, sebagian besar membaca tabel yang mungkin memiliki kode string panjang statis yang unik, atau nilai numerik seperti tahun atau angka lainnya.

Untuk sebagian besar, semua tabel lainnya akan memiliki bilangan bulat peningkatan otomatis atau kunci primer pengidentifikasi unik.

Pertanyaan :-)

Saya baru-baru ini mulai bekerja dengan database yang tidak memiliki pengidentifikasi baris yang konsisten dan kunci primer saat ini dikelompokkan di berbagai kolom. Beberapa contoh:

  • datetime / karakter
  • datetime / integer
  • datetime / varchar
  • char / nvarchar / nvarchar

Apakah ada kasus yang valid untuk ini? Saya akan selalu mendefinisikan kolom identitas atau pengidentifikasi unik untuk kasus-kasus ini.

Selain itu ada banyak tabel tanpa kunci primer sama sekali. Apa alasan yang valid, jika ada, untuk ini?

Saya mencoba untuk memahami mengapa tabel dirancang sebagaimana mestinya, dan tampaknya menjadi kekacauan besar bagi saya, tapi mungkin ada alasan bagus untuk itu.

Pertanyaan ketiga untuk menyortir membantu saya menguraikan jawaban: Dalam kasus di mana banyak kolom digunakan untuk menyusun kunci primer majemuk, apakah ada keunggulan spesifik untuk metode ini vs kunci pengganti / buatan? Saya berpikir sebagian besar dalam hal kinerja, pemeliharaan, administrasi, dll?


Saya menemukan Keterampilan Basis Data: Pendekatan yang Sehat untuk Memilih Kunci Utama sebagai bacaan yang baik dan saya mengikuti sebagian besar poin yang diuraikan.
user2864740

Jawaban:


254

Saya mengikuti beberapa aturan:

  1. Kunci primer harus sekecil yang diperlukan. Lebih suka tipe numerik karena tipe numerik disimpan dalam format yang jauh lebih ringkas daripada format karakter. Ini karena sebagian besar kunci utama akan menjadi kunci asing di tabel lain serta digunakan dalam banyak indeks. Semakin kecil kunci Anda, semakin kecil indeksnya, semakin sedikit halaman dalam cache yang akan Anda gunakan.
  2. Kunci primer tidak boleh berubah. Memperbarui kunci utama harus selalu keluar dari pertanyaan. Ini karena kemungkinan besar akan digunakan dalam beberapa indeks dan digunakan sebagai kunci asing. Memperbarui kunci primer tunggal dapat menyebabkan efek perubahan riak.
  3. JANGAN gunakan "kunci utama masalah Anda" sebagai kunci utama model logika Anda. Misalnya nomor paspor, nomor jaminan sosial, atau nomor kontrak karyawan karena "kunci utama" ini dapat berubah untuk situasi dunia nyata.

Pada kunci pengganti vs alami, saya merujuk pada aturan di atas. Jika kunci alami kecil dan tidak akan pernah berubah, dapat digunakan sebagai kunci utama. Jika kunci alami besar atau cenderung berubah, saya menggunakan kunci pengganti. Jika tidak ada kunci utama saya masih membuat kunci pengganti karena pengalaman menunjukkan Anda akan selalu menambahkan tabel ke skema Anda dan berharap Anda akan meletakkan kunci utama di tempat.


3
Saya suka itu! Apakah Anda memiliki dokumentasi untuk dasar "aturan" Anda? Terima kasih!
Lloyd Cotten

4
Tidak, hanya pengalaman. Ketika berhadapan dengan database "kecil", hal ini tidak terlalu menjadi masalah. Tetapi ketika Anda berurusan dengan db besar semua hal kecil itu penting. Bayangkan saja jika Anda memiliki 1 miliar baris dengan pk int atau panjang dibandingkan dengan menggunakan teks atau panduan. Ada perbedaan besar!
Logicalmind

44
Hanya ingat untuk meletakkan indeks unik pada kunci alami (jika ada yang benar-benar sering terjadi) ketika Anda menggunakan kunci buatan.
HLGEM

3
@Lloyd Cotten: Inilah yang dikatakan penyedia mesin data besar untuk mendukung aturan nomor 1: skyfoundry.com/forum/topic/24 . Itu meyakinkan saya untuk kembali ke Ints
hobs

4
bahkan jika Anda "tahu" bahwa "kunci alami itu kecil dan tidak akan pernah berubah", pikirkan dua kali. "kami tidak pernah menggunakan kembali kode-kode itu" adalah kata-kata terakhir yang terkenal .... Tentang satu-satunya hal yang termasuk dalam kategori kecil, tidak pernah berubah adalah iso dan standar lainnya (kode negara, kode bandara iata,). Hal-hal seperti "apa representasi 2 huruf untuk merek internal ini" ... pikirkan dua kali sebelum berasumsi bahwa "itu" tidak akan pernah berubah, Anda satu keputusan keuangan jauh dari pembangunan kembali basis data.
Andrew Hill

90

Kunci artifisial ayat-ayat alami adalah sejenis perdebatan agama di antara komunitas basis data - lihat artikel ini dan tautan lainnya yang terkait. Saya tidak mendukung selalu memiliki kunci buatan, atau tidak pernah memilikinya. Saya akan memutuskan berdasarkan kasus per kasus, misalnya:

  • Amerika Serikat: Saya akan menggunakan state_code ('TX' untuk Texas dll.), Daripada state_id = 1 untuk Texas
  • Karyawan: Saya biasanya membuat employee_id buatan, karena sulit menemukan hal lain yang berfungsi. SSN atau yang setara mungkin berfungsi, tetapi mungkin ada masalah seperti joiner baru yang belum menyediakan SSN-nya.
  • Riwayat Gaji Karyawan: (employee_id, start_date). Saya tidak akan membuat employee_salary_history_id buatan. Apa gunanya (selain "konsistensi bodoh" )

Di mana pun kunci buatan digunakan, Anda harus selalu menyatakan batasan unik pada kunci alami. Misalnya, gunakan state_id jika Anda harus, tetapi lebih baik Anda mendeklarasikan batasan unik pada state_code, jika tidak, Anda pasti akan berakhir dengan:

state_id    state_code   state_name
137         TX           Texas
...         ...          ...
249         TX           Texas

9
Dalam beberapa kasus dengan SQL server 2005/2008 kunci (teks) alami bisa lebih cepat daripada kunci int. Saya memiliki aplikasi dengan kode ramah karakter 7-8 yang kami gunakan sebagai kunci utama dan itu lebih cepat (dan sering lebih nyaman) daripada pengganti int. Kami tetap membutuhkan kode tersebut sehingga kami dapat memiliki kode yang dapat dibaca / diingat manusia yang dapat kami transfer dengan aman tanpa konflik ke instance aplikasi yang berbeda (beberapa situs yang menggabungkan ke situs yang lebih besar).
lambacck

1
+1 Jawaban yang bagus. Namun, saya akan membuat petugas personalia menjadi sumber tepercaya dari pengidentifikasi karyawan yaitu petugas yang bertanggung jawab untuk memverifikasi karyawan dalam kehidupan nyata yang cenderung menggunakan pengidentifikasi seperti SSN, mengambil referensi, dll. Departemen personalia harus dipercayai sumber pengidentifikasi karyawan, bukan DBMS!
onedaywhen

@ onedaywhen- saya tidak akan. percaya pada petugas personalia. Orang-orang pergi, yang baru datang dan punya ide berbeda. Berikan mereka akses ke pengenal yang menurut mereka unik / ingin mereka gunakan, tetapi secara internal untuk db, dba harus membuat keputusan sendiri
Dave Pile

1
Perhatikan bahwa SSN tidak harus unik di setiap negara. Setidaknya di Austria, banyak orang mungkin memiliki nomor yang sama
maja

Juga di beberapa negara (saya pikir bahkan di AS) mereka benar-benar merekomendasikan untuk tidak berbagi SSN.
Stijn de Witt

25

Hanya komentar tambahan tentang sesuatu yang sering diabaikan. Terkadang tidak menggunakan kunci pengganti memiliki manfaat di tabel anak. Katakanlah kita memiliki desain yang memungkinkan Anda menjalankan banyak perusahaan dalam satu basis data (mungkin itu solusi yang di-host, atau apa pun).

Katakanlah kita memiliki tabel dan kolom ini:

Company:
  CompanyId   (primary key)

CostCenter:
  CompanyId   (primary key, foreign key to Company)
  CostCentre  (primary key)

CostElement
  CompanyId   (primary key, foreign key to Company)
  CostElement (primary key)

Invoice:
  InvoiceId    (primary key)
  CompanyId    (primary key, in foreign key to CostCentre, in foreign key to CostElement)
  CostCentre   (in foreign key to CostCentre)
  CostElement  (in foreign key to CostElement)

Jika bit terakhir tidak masuk akal, Invoice.CompanyIdadalah bagian dari dua kunci asing, satu ke tabel CostCentre dan satu ke tabel CostElement . Kunci utama adalah ( InvoiceId , CompanyId ).

Dalam model ini, tidak mungkin untuk mengacaukan dan merujuk CostElement dari satu perusahaan dan CostCentre dari perusahaan lain. Jika kunci pengganti digunakan pada CostElement dan meja CostCentre , itu akan menjadi.

Semakin sedikit peluang untuk mengacau, semakin baik.


6
Ini adalah kelemahan yang kurang dikutip saat menggunakan kunci pengganti. Jika tabel memiliki kunci pengganti, saya masih bisa menggunakannya untuk kendala semacam ini. Sayangnya meskipun kendala membutuhkan indeks dan itu hanya aneh untuk membuat indeks unik pada (surrogate_key, other_column) ketika (surrogate_key) unik dengan sendirinya. Juga, (other_column) sering benar-benar berlebihan di tabel peta karena (surrogate_key) unik di yang asing. Pengganti benar-benar dapat membereskan semuanya.
Samuel Danielson

24

Saya menghindari menggunakan kunci alami karena satu alasan sederhana - kesalahan manusia. Meskipun pengidentifikasi unik alami sering tersedia (SSN, VIN, Nomor Akun, dll.), Mereka membutuhkan manusia untuk memasukkannya dengan benar. Jika Anda menggunakan SSN sebagai kunci utama, seseorang mentranspos beberapa angka selama entri data, dan kesalahan tidak segera ditemukan, maka Anda dihadapkan dengan perubahan kunci primer.

Kunci utama saya semua ditangani oleh program database di latar belakang dan pengguna tidak pernah menyadarinya.


1
Saya telah bekerja dengan beberapa database yang menggunakan SSN atau ID Pajak sebagai kunci utama. Tidak efisien dalam hal penyimpanan dan referensi kunci asing. Belum lagi bahwa SSN seseorang dapat berubah. Jadi saya sepenuhnya setuju dengan Anda.
Alex Jorgenson

13

Tidak ada masalah dalam membuat kunci utama Anda dari berbagai bidang, itu adalah Kunci Alami .

Anda dapat menggunakan kolom Identitas (terkait dengan indeks unik pada bidang kandidat) untuk membuat Kunci Pengganti .

Itu diskusi lama. Saya lebih suka kunci pengganti dalam sebagian besar situasi.

Tapi tidak ada alasan untuk tidak memiliki kunci.

RE: EDIT

Ya, ada banyak kontroversi tentang itu: D

Saya tidak melihat keuntungan nyata pada kunci alami, selain fakta bahwa mereka adalah pilihan alami. Anda akan selalu berpikir dalam Name, SocialNumber - atau sesuatu seperti itu - bukan idPerson .

Kunci pengganti adalah jawaban untuk beberapa masalah yang dimiliki kunci alami (menyebarkan perubahan misalnya).

Ketika Anda terbiasa dengan ibu pengganti, tampaknya lebih bersih, dan dapat dikelola.

Tetapi pada akhirnya, Anda akan menemukan bahwa itu hanya masalah selera - atau pola pikir -. Orang "berpikir lebih baik" dengan kunci alami, dan yang lain tidak.


13
Orang-orang "berpikir lebih baik" dengan kunci alami. Mesin dan database, jangan.
FDCastel

11

Tabel harus memiliki kunci utama setiap saat. Ketika tidak, seharusnya merupakan bidang AutoIncrement.

Kadang-kadang orang menghilangkan kunci utama karena mereka mentransfer banyak data dan itu mungkin memperlambat (tergantung dari database) prosesnya. NAMUN, itu harus ditambahkan setelah itu.

Seseorang berkomentar tentang tabel tautan , ini benar, itu pengecualian TETAPI bidang harus FK untuk menjaga integritas, dan kadang-kadang bidang-bidang itu bisa menjadi kunci utama juga jika duplikat di tautan tidak diotorisasi ... tetapi untuk tetap dalam bentuk sederhana karena pengecualian adalah sesuatu yang sering dalam pemrograman, kunci utama harus ada untuk menjaga integritas data Anda.


Saya setuju. Dan dalam kasus di mana banyak data akan dimasukkan, hapus batasan kunci primer (atau gunakan INSERT IDENTITY ON di TSQL) dan masukkan kembali sesudahnya :)
Andrew Rollings

1
Ada pengecualian: tabel tautan jelas
annakata

Alasan lain: Jika tidak ada kunci PK / unik, browser tabel (maksud saya, sesuatu seperti Access / SQL Server Management Studio) akan menolak untuk memperbarui / menghapus satu baris dengan baris yang digandakan. Anda harus menulis SQL untuk itu.
Dennis C

Sangat umum untuk menghilangkan PK dari tabel fakta data warehouse. Dalam Oracle, Anda dapat merujuk pseudocolumn ROWID sebagai pengidentifikasi unik dalam jangka pendek (mis. Jangan menyimpannya di suatu tempat dan berharap itu tidak berubah)
David Aldridge

9

Selain semua jawaban yang bagus itu, saya hanya ingin membagikan artikel bagus yang baru saja saya baca, Debat utama yang hebat .

Hanya mengutip beberapa poin:

Pengembang harus menerapkan beberapa aturan saat memilih kunci utama untuk setiap tabel:

  • Kunci utama harus secara unik mengidentifikasi setiap catatan.
  • Nilai kunci utama rekaman tidak boleh nol.
  • Nilai kunci utama harus ada saat catatan dibuat.
  • Kunci utama harus tetap stabil — Anda tidak dapat mengubah bidang kunci utama.
  • Kunci utama harus ringkas dan mengandung atribut sesedikit mungkin.
  • Nilai kunci utama tidak dapat diubah.

Kunci alami (cenderung) melanggar aturan. Kunci pengganti mematuhi aturan. (Lebih baik Anda membaca artikel itu, sangat berharga untuk waktu Anda!)


7

Apa yang spesial dari kunci primer?

Apa tujuan dari tabel dalam suatu skema? Apa tujuan dari kunci tabel? Apa yang spesial dari kunci primer? Diskusi seputar kunci primer tampaknya melewatkan poin bahwa kunci utama adalah bagian dari sebuah tabel, dan tabel itu adalah bagian dari skema. Apa yang terbaik untuk hubungan tabel dan tabel harus mendorong kunci yang digunakan.

Tabel (dan hubungan tabel) berisi fakta tentang informasi yang ingin Anda rekam. Fakta-fakta ini harus mandiri, bermakna, mudah dipahami, dan tidak kontradiktif. Dari perspektif desain, tabel lain yang ditambahkan atau dihapus dari skema tidak boleh berdampak pada tabel yang dimaksud. Harus ada tujuan untuk menyimpan data yang terkait hanya dengan informasi itu sendiri. Memahami apa yang disimpan dalam sebuah tabel seharusnya tidak perlu menjalani proyek penelitian ilmiah. Tidak ada fakta yang disimpan untuk tujuan yang sama harus disimpan lebih dari satu kali. Kunci adalah seluruh atau bagian dari informasi yang direkam yang unik, dan kunci primer adalah kunci yang ditunjuk khusus yang menjadi titik akses utama ke tabel (yaitu harus dipilih untuk konsistensi dan penggunaan data, bukan hanya memasukkan kinerja).

  • ASIDE: Sayangnya efek samping dari sebagian besar basis data sedang dirancang dan dikembangkan oleh pemrogram aplikasi (yang kadang-kadang saya) adalah bahwa apa yang terbaik untuk aplikasi atau kerangka kerja aplikasi sering mendorong pilihan kunci utama untuk tabel. Ini mengarah ke kunci integer dan GUID (karena ini mudah digunakan untuk kerangka kerja aplikasi) dan desain tabel monolitik (karena ini mengurangi jumlah objek kerangka kerja aplikasi yang diperlukan untuk mewakili data dalam memori). Keputusan desain database yang digerakkan aplikasi ini mengarah pada masalah konsistensi data yang signifikan ketika digunakan pada skala. Kerangka kerja aplikasi yang dirancang dengan cara ini secara alami mengarah ke meja pada suatu waktu desain. "Catatan parsial" dibuat dalam tabel dan data diisi seiring waktu. Interaksi multi-tabel dihindari atau ketika digunakan menyebabkan data tidak konsisten ketika fungsi aplikasi tidak benar. Desain ini mengarah pada data yang tidak berarti (atau sulit dipahami), data tersebar di atas tabel (Anda harus melihat tabel lain untuk memahami tabel saat ini), dan data duplikat.

Dikatakan bahwa kunci primer harus sekecil yang diperlukan. Saya akan mengatakan bahwa kunci harus hanya sebesar yang diperlukan. Menambahkan bidang yang tidak bermakna secara acak ke tabel harus dihindari. Lebih buruk lagi untuk membuat kunci dari bidang yang tidak bermakna yang ditambahkan secara acak, terutama ketika itu menghancurkan ketergantungan gabungan dari tabel lain ke kunci non-primer. Ini hanya masuk akal jika tidak ada kunci kandidat yang baik dalam tabel, tetapi kejadian ini pasti merupakan tanda dari desain skema yang buruk jika digunakan untuk semua tabel.

Juga dikatakan bahwa kunci primer tidak boleh berubah karena memperbarui kunci primer harus selalu keluar dari pertanyaan. Tetapi pembaruan sama dengan hapus diikuti dengan menyisipkan. Dengan logika ini, Anda seharusnya tidak pernah menghapus catatan dari tabel dengan satu kunci dan kemudian menambahkan catatan lain dengan kunci kedua. Menambahkan kunci primer pengganti tidak menghilangkan fakta bahwa kunci lain dalam tabel ada. Memperbarui kunci non-primer dari sebuah tabel dapat menghancurkan makna data jika tabel lain memiliki ketergantungan pada makna tersebut melalui kunci pengganti (misalnya tabel status dengan kunci pengganti yang uraian statusnya diubah dari 'Diproses' menjadi 'Dibatalkan 'Pasti akan merusak data). Apa yang harus selalu keluar dari pertanyaan adalah menghancurkan makna data.

Setelah mengatakan ini, saya berterima kasih atas banyak database yang dirancang dengan buruk yang ada dalam bisnis saat ini (raksasa tak berarti-kunci-data-rusak-1NF), karena itu berarti ada banyak pekerjaan untuk orang-orang yang memahami desain database yang tepat . Tapi di sisi yang menyedihkan, itu kadang-kadang membuatku merasa seperti Sisyphus, tapi aku yakin dia punya satu 401k (sebelum kecelakaan). Jauhi blog dan situs web untuk pertanyaan desain database penting. Jika Anda mendesain database, lihat CJ Date. Anda juga bisa mereferensikan Celko untuk SQL Server, tetapi hanya jika Anda lebih memilih. Di sisi Oracle, rujuk Tom Kyte.


1
"Dengan logika ini, Anda seharusnya tidak pernah menghapus catatan dari tabel dengan satu kunci dan kemudian menambahkan catatan lain dengan kunci kedua." - Ada kasus untuk ini, dan itu efektif apa yang klausa "ON DELETE RESTRICT" pada kunci asing akan dilakukan. Dalam beberapa kasus (katakanlah di mana jejak audit diperlukan), bidang boolean "dihapus" akan lebih baik daripada membiarkan catatan dihapus.
Waz

6

Kunci alami, jika tersedia, biasanya yang terbaik. Jadi, jika datetime / char secara unik mengidentifikasi baris dan kedua bagian itu bermakna bagi baris, itu bagus.

Jika hanya datetime yang berarti, dan char hanya ditempel untuk membuatnya unik, maka Anda mungkin juga pergi dengan bidang identifikasi.


9
Biasanya yang terbaik? Saya tidak memiliki dasar ilmiah tetapi saya hampir positif kebanyakan orang lebih memilih kunci pengganti daripada alami. Dalam banyak kasus tidak ada kunci alami.
JC.

3
Seharusnya SELALU menjadi kunci alami untuk setiap baris dalam basis data Anda. Kunci "alami" itu mungkin sesuatu yang dihasilkan di dunia bisnis atau oleh sistem teknis Anda, tetapi harus selalu ada.
Tom H

2
Jika, di dunia Anda, itulah yang telah ditentukan sebagai satu-satunya cara untuk mengidentifikasi baris dalam tabel, maka ya. Tentu saja, ketika seorang desainer memilih untuk membuat GUID untuk PK itu biasanya karena mereka belum melakukan pekerjaan untuk menemukan kunci alami NYATA, jadi dalam kasus itu GUID BUKAN kunci alami.
Tom H

8
2. Jika Anda mengambil kunci dari dunia alami, dunia alami akan berubah untuk memecahkan kunci Anda. Jika Anda menggunakan nomor telepon, Anda akan mendapatkan dua pengguna dari rumah tangga yang sama. Jika Anda menggunakan nama belakang, mereka menikah. Jika Anda menggunakan SSN, undang-undang privasi akan berubah dan mengharuskan Anda menghapusnya.
James Orr

2
@Barry: RE: # 2. jika dunia alami berubah dan itu menyebabkan kunci alami Anda berubah, itu berarti Anda melakukan pekerjaan yang buruk dalam memilih kunci alami. Menurut definisi, kunci alami tidak berubah seiring waktu.
Tom H

6

Berikut adalah aturan praktis saya sendiri yang telah saya tentukan setelah 25+ tahun pengalaman pengembangan.

  • Semua tabel harus memiliki kunci utama kolom tunggal yang bertambah secara otomatis.
  • Sertakan dalam tampilan apa pun yang dimaksudkan untuk dapat diperbarui
  • Kunci utama tidak boleh memiliki makna dalam konteks aplikasi Anda. Ini berarti bahwa itu tidak boleh SKU, atau nomor akun atau id karyawan atau informasi lain yang bermakna bagi aplikasi Anda. Ini hanyalah kunci unik yang terkait dengan suatu entitas.

Kunci utama digunakan oleh basis data untuk keperluan optimasi dan tidak boleh digunakan oleh aplikasi Anda untuk apa pun selain mengidentifikasi entitas tertentu atau yang berkaitan dengan entitas tertentu.

Selalu memiliki kunci primer nilai tunggal membuat kinerja UPSERT sangat mudah.

Gunakan indeks tambahan untuk mendukung kunci multi-kolom yang memiliki arti dalam aplikasi Anda.


5

Kunci alami versus buatan bagi saya adalah masalah seberapa banyak logika bisnis yang Anda inginkan dalam database Anda. Nomor Jaminan Sosial (SSN) adalah contoh yang bagus.

"Setiap klien dalam database saya akan, dan harus, memiliki SSN." Bam, selesai, jadikan itu kunci utama dan selesai dengan itu. Ingat saja ketika aturan bisnis Anda berubah Anda dibakar.

Saya sendiri tidak suka kunci alami, karena pengalaman saya dengan perubahan aturan bisnis. Tetapi jika Anda yakin itu tidak akan berubah, itu mungkin mencegah beberapa bergabung kritis.


8
Dan saya telah melihat data di mana SSN tidak unik meskipun seharusnya. Berhati-hatilah terhadap kunci alam jika Anda mengimpor data dari sumber lain!
HLGEM

2
Jika Anda mengalami pencurian identitas, nomor jaminan sosial Anda dapat diubah. Ada empat situasi lagi di mana mereka akan mengubah nomor Anda dan mereka terdaftar di situs ssa.gov.
Zvi Twersky

4

Saya curiga terapi koran Steven A. Lowe yang digulung diperlukan untuk perancang struktur data asli.

Selain itu, GUID sebagai kunci utama dapat menjadi babi kinerja. Saya tidak akan merekomendasikannya.


2
Untuk mengatakan ini adalah babi kinerja adalah optimasi prematur. Dalam beberapa kasus diperlukan panduan (klien terputus, penggabungan tabel di masa mendatang, replikasi)
JC.

2
"Optimasi prematur" adalah frasa yang terlalu sering digunakan pada SO (IMHO)! Ya, GUID mungkin diperlukan dalam BEBERAPA kasus, tetapi Andrew benar untuk menunjukkan bahwa mereka tidak boleh digunakan sebagai tipe data default apakah diperlukan atau tidak.
Tony Andrews

OKE, itu sebenarnya bukan optimasi prematur. Yang saya maksudkan adalah bahwa kebanyakan orang tidak mengalami volume yang diperlukan untuk memperhatikan perbedaan kinerja. Ya, gunakan peningkatan otomatis jika Anda tahu Anda tidak akan pernah membutuhkan panduan.
JC.

Atau gunakan keduanya. Memiliki kunci utama berbasis int / panjang untuk memilih cepat dan bergabung dengan baik, dan kemudian memiliki bidang panduan. Setidaknya, itulah yang saya lakukan. Apakah ini salah? Haruskah saya tidak melakukan itu? :)
Andrew Rollings

Saya juga menggunakan kedua kolom. Tetapi tidak yakin apakah itu salah atau tidak. Apakah Anda menemukannya @AndrewRollings?
YÒGÎ

3

Anda harus menggunakan kunci primer 'gabungan' atau 'majemuk' yang terdiri dari beberapa bidang.

Ini adalah solusi yang bisa diterima, buka di sini untuk info lebih lanjut :)


3

Saya juga selalu menggunakan kolom ID numerik. Dalam oracle saya menggunakan angka (18,0) tanpa alasan sebenarnya di atas angka (12,0) (atau apa pun yang merupakan int daripada panjang), mungkin saya hanya tidak ingin pernah khawatir mendapatkan beberapa miliar baris dalam db!

Saya juga menyertakan kolom yang dibuat dan dimodifikasi (jenis cap waktu) untuk pelacakan dasar, yang sepertinya bermanfaat.

Saya tidak keberatan mengatur batasan unik pada kombinasi kolom lainnya, tapi saya sangat suka id saya, dibuat, persyaratan dasar yang dimodifikasi.


2
Saya juga harus menunjukkan bahwa saya tidak menaruh ID pada tautan / gabung tabel, hanya pada tabel yang berisi data.
JeeBee

3

Saya mencari kunci primer alami dan menggunakannya di mana saya bisa.

Jika tidak ada kunci alami dapat ditemukan, saya lebih suka GUID ke INT ++ karena SQL Server menggunakan pohon, dan itu buruk untuk selalu menambahkan kunci ke ujung pohon.

Pada tabel yang banyak-ke-banyak kopling saya menggunakan kunci utama gabungan dari kunci asing.

Karena saya cukup beruntung menggunakan SQL Server, saya dapat mempelajari rencana dan statistik eksekusi dengan profiler dan penganalisis kueri dan mencari tahu bagaimana kinerja kunci saya dengan sangat mudah.


Apakah Anda memiliki dokumentasi untuk mendukung pernyataan ini: 'jika tidak ada kunci alami dapat ditemukan, saya lebih suka GUID ke INT ++ karena SQL Server menggunakan pohon, dan itu buruk untuk selalu menambahkan kunci ke akhir di pohon.' Tidak skeptis, hanya mencoba mengkompilasi beberapa dokumentasi.
Lloyd Cotten

1
@Lloyd - Senang Anda tertarik pada sesuatu yang saya temukan sangat menarik. Titik awal yang baik di msdn.microsoft.com/en-us/library/ms177443(SQL.90).aspx
Guge

2

Saya selalu menggunakan bidang autonumber atau identitas.

Saya bekerja untuk klien yang telah menggunakan SSN sebagai kunci utama dan kemudian karena peraturan HIPAA dipaksa untuk berubah menjadi "MemberID" dan itu menyebabkan banyak masalah ketika memperbarui kunci asing di tabel terkait. Berpegang teguh pada standar kolom identitas yang konsisten telah membantu saya menghindari masalah serupa di semua proyek saya.


6
Pilihan kunci alami yang buruk oleh pengembang tidak berarti bahwa kunci alami itu buruk.
Tom H

1
Alat yang sulit digunakan, entah bagaimana, bukan suatu titik terhadap alat itu?
Sqeaky

1

Semua tabel harus memiliki kunci utama. Kalau tidak, apa yang Anda miliki adalah HEAP - ini, dalam beberapa situasi, mungkin apa yang Anda inginkan (beban memasukkan yang berat ketika data kemudian direplikasi melalui broker layanan ke database atau tabel lain misalnya).

Untuk tabel pencarian dengan volume baris yang rendah, Anda dapat menggunakan kode 3 CHAR sebagai kunci utama karena ini membutuhkan lebih sedikit ruang daripada INT, tetapi perbedaan kinerja dapat diabaikan. Selain itu, saya akan selalu menggunakan INT kecuali Anda memiliki tabel referensi yang mungkin memiliki kunci primer komposit yang dibuat dari kunci asing dari tabel terkait.


1

Jika Anda benar-benar ingin membaca semua bolak-balik pada perdebatan kuno ini, lakukan pencarian untuk "kunci alami" di Stack Overflow. Anda harus mendapatkan kembali halaman hasil.


1

GUID dapat digunakan sebagai kunci utama, tetapi Anda harus membuat tipe GUID yang tepat agar kinerjanya baik.

Anda perlu membuat PANDUAN COMB. Artikel bagus tentang itu dan statistik kinerja adalah The Cost of GUIDs sebagai Primary Key .

Juga beberapa kode untuk membangun GUB COMB dalam SQL adalah dalam Uniqueidentifier vs identitas ( arsip ) .


5
IMHO, guid hanya boleh digunakan ketika Anda perlu menyinkronkan data di seluruh database. Di mana id yang dihasilkan secara otomatis bermasalah. Perbedaan antara menggunakan pedoman dan menggunakan tipe numerik dasar adalah bahwa panduan akan membutuhkan 16 byte per baris, sedangkan numerik akan jauh lebih kecil.
Logicalmind

Jika Anda membuka tautan yang saya berikan di atas, ada sedikit perbedaan dalam kinerja menggunakan Panduan COMB.
Donny V.

0

Kami melakukan banyak gabungan dan kunci primer komposit baru saja menjadi babi kinerja. Int sederhana atau panjang menangani banyak masalah meskipun Anda memperkenalkan kunci kandidat kedua, tetapi jauh lebih mudah dan lebih mudah untuk bergabung dalam satu bidang versus tiga.


1
Strategi ini berantakan ketika Anda sekarang harus melintasi 6 tabel untuk bergabung dengan dua tabel sebenarnya yang Anda butuhkan karena kunci komposit tidak disebarkan. Itu juga akhirnya membutuhkan penggunaan loop / kursor untuk beberapa sisipan yang dapat menjadi babi kinerja BESAR.
Tom H

2
Saya tidak terlalu besar untuk belajar sesuatu yang baru. Saya ingin melihat contoh dari apa yang Anda katakan, akan sangat membantu untuk memasukkan sedikit fakta rasional ke dalam beberapa argumen keagamaan ini.
Dan Blair

0

Saya akan mengedepankan preferensi saya untuk kunci alami - gunakan jika memungkinkan, karena akan membuat hidup Anda dalam administrasi basis data jauh lebih mudah. Saya menetapkan standar di perusahaan kami bahwa semua tabel memiliki kolom berikut:

  • ID Baris (GUID)
  • Pembuat (string; memiliki default nama pengguna saat ini ( SUSER_SNAME()dalam T-SQL))
  • Dibuat (DateTime)
  • Stempel waktu

ID Baris memiliki kunci unik di atasnya per tabel, dan dalam hal apa pun dihasilkan secara otomatis per baris (dan izin mencegah siapa pun mengeditnya), dan dijamin masuk akal untuk unik di semua tabel dan database. Jika ada sistem ORM yang membutuhkan kunci ID tunggal, ini yang akan digunakan.

Sementara itu, PK yang sebenarnya, jika mungkin, adalah kunci alami. Aturan internal saya adalah seperti:

  • Orang - gunakan kunci pengganti, misalnya INT. Jika internal, GUID pengguna Active Directory adalah pilihan yang dapat diterima
  • Tabel pencarian (mis. StatusCodes) - gunakan kode CHAR pendek; lebih mudah diingat daripada INT, dan dalam banyak kasus, formulir dan pengguna kertas juga akan menggunakannya untuk singkatnya (misalnya Status = "E" untuk "Kedaluwarsa", "A" untuk "Disetujui", "NADIS" untuk "Tidak Terdeteksi Asbes" Dalam Sampel ")
  • Menautkan tabel - kombinasi FK (misalnya EventId, AttendeeId)

Jadi idealnya Anda berakhir dengan PK alami, dapat dibaca oleh manusia dan mudah diingat, dan GUID satu-ID-per-tabel yang ramah ORM.

Peringatan: database yang saya kelola cenderung ke 100.000 catatan daripada jutaan atau miliaran, jadi jika Anda memiliki pengalaman sistem yang lebih besar yang kontraindikasi saran saya, jangan ragu untuk mengabaikan saya!


1
Apakah Anda menyarankan untuk membuat keduanya GUID dan INT SK untuk tabel tanpa kunci alami yang kuat?

Anda tidak harus melakukannya, tetapi manfaatnya adalah: a) itu membuat replikasi lebih mudah jika Anda membutuhkannya, b) ketika berurusan dengan ORM, Anda dapat menetapkan ID unik untuk objek Anda dalam kode sebelum menyimpannya (yang berguna jika Anda harus melakukan banyak pengeditan pada objek Anda, mungkin menyimpan ke dalam cache sesi, sebelum menyimpannya). Kuncinya adalah INT dalam hal ini; GUID hanyalah bonus.
Keith Williams
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.