Klucze obce - link przy użyciu klucza zastępczego lub naturalnego?

14

Czy istnieje najlepsza praktyka dotycząca tego, czy klucz obcy między tabelami powinien łączyć się z kluczem naturalnym czy kluczem zastępczym? Jedyną dyskusją, którą naprawdę znalazłem (chyba że brakuje mi google-fu), jest odpowiedź Jacka Douglasa na to pytanie , a jego rozumowanie wydaje mi się słuszne. Zdaję sobie sprawę z dyskusji, że zasady się zmieniają, ale byłoby to coś, co należałoby rozważyć w każdej sytuacji.

Głównym powodem pytania jest to, że mam starszą aplikację, która korzysta z FK z naturalnymi kluczami, ale devlopers są silnie naciskani, aby przejść do OR / M (NHibernate w naszym przypadku), a widelec już wyprodukował trochę przełamując zmiany, więc chcę przesunąć je z powrotem na ścieżkę za pomocą naturalnego klucza lub przenieść starszą aplikację, aby używać klawiszy zastępczych dla FK. Moje wnętrzności mówią o przywróceniu oryginalnego FK, ale szczerze mówiąc, nie jestem pewien, czy to naprawdę właściwa ścieżka.

Większość naszych tabel ma już zdefiniowany zarówno klucz zastępczy, jak i naturalny (chociaż unikalne ograniczenie i PK), więc konieczność dodania dodatkowych kolumn nie jest dla nas problemem w tym ubezpieczeniu. Korzystamy z programu SQL Server 2008, ale mam nadzieję, że jest to dość ogólne dla dowolnej bazy danych.

Chris J
źródło

Odpowiedzi:

15

Ani SQL, ani model relacyjny nie są zakłócane przez klucze obce, które odwołują się do klucza naturalnego. W rzeczywistości odwoływanie się do naturalnych kluczy często znacznie poprawia wydajność. Byłbyś zaskoczony, jak często potrzebne informacje są całkowicie zawarte w naturalnym kluczu; odwołanie się do tego klucza powoduje zamianę złączenia na szerszą tabelę (i w konsekwencji zmniejsza liczbę wierszy, które można przechowywać na jednej stronie).

Z definicji potrzebne informacje są zawsze całkowicie zawarte w naturalnym kluczu każdej tabeli „wyszukiwania”. (Pojęcie tabela odnośników jest nieformalne. W modelu relacyjnym wszystkie tabele są tylko tabelami. Tabela kodów pocztowych w USA może mieć wiersze wyglądające tak: {AK, Alaska}, {AL, Alabama}, {AZ, Arizona} itp. Większość osób nazwałaby to tabelą odnośników).

W dużych systemach często zdarza się, że tabele mają więcej niż jeden klucz kandydujący. Nie jest niczym niezwykłym, że tabele, które służą jednej części przedsiębiorstwa, odnoszą się do jednego klucza kandydującego, a tabele, które służą innej części przedsiębiorstwa, do odwołania się do innego klucza kandydującego. Jest to jedna z mocnych stron modelu relacyjnego i jest to część modelu relacyjnego, który dość dobrze obsługuje SQL.

Podczas odwoływania się do kluczy naturalnych w tabelach, które również mają klucz zastępczy, napotkasz dwa problemy.

Najpierw zaskoczysz ludzi. Chociaż zwykle mocno lobbuję za zasadą najmniejszej niespodzianki , jest to jedna sytuacja, w której nie mam nic przeciwko zaskakującym ludziom. Gdy problem polega na tym, że programiści są zaskoczeni logicznym użyciem kluczy obcych, rozwiązaniem jest edukacja, a nie przeprojektowanie.

Po drugie, ORM nie są na ogół projektowane wokół modelu relacyjnego i czasami zawierają założenia, które nie odzwierciedlają najlepszych praktyk. (W rzeczywistości często wydaje się, że zostały zaprojektowane bez potrzeby korzystania z danych specjalisty od bazy danych). Wymaganie numeru identyfikacyjnego w każdej tabeli jest jednym z tych założeń. Kolejny zakłada, że ​​aplikacja ORM „jest właścicielem” bazy danych. (Więc tworzenie, usuwanie i zmiana nazw tabel i kolumn jest bezpłatne).

Pracowałem nad systemem baz danych, który przez 30 lat obsługiwał dane setek programów aplikacyjnych napisanych w co najmniej dwóch tuzinach języków. Ta baza danych należy do przedsiębiorstwa, a nie do ORM.

Widelec, który wprowadza przełomowe zmiany, powinien być przeszkodą.

Zmierzyłem wydajność zarówno przy użyciu kluczy naturalnych, jak i zastępczych w firmie, w której pracowałem. Jest punkt zwrotny, w którym klucze zastępcze zaczynają przewyższać klucze naturalne. (Zakładając, że nie będzie żadnych dodatkowych wysiłków w celu utrzymania wysokiej wydajności naturalnego klucza, takich jak partycjonowanie, indeksy częściowe, indeksy oparte na funkcjach, dodatkowe przestrzenie tabel, używanie dysków półprzewodnikowych itp.) Według moich szacunków dla tej firmy osiągną ten punkt zwrotny w około 2045. W międzyczasie uzyskują lepszą wydajność dzięki naturalnym kluczom.

Inne istotne odpowiedzi: w mylącym schemacie bazy danych

Mike Sherrill „Cat Recall”
źródło
5

Głównym powodem, dla którego popieram klucze zastępcze, jest to, że klucze naturalne często podlegają zmianom, co oznacza, że ​​wszystkie powiązane tabele muszą zostać zaktualizowane, co może znacznie obciążać serwer.

Co więcej, w ciągu 30 lat korzystałem z różnych baz danych na wiele tematów, prawdziwy naturalny klucz jest często dość rzadki. Rzeczy rzekomo unikalne (SSN) nie są, rzeczy, które są unikalne w danym momencie, mogą później stać się nieunikalne, a niektóre rzeczy, takie jak adresy e-mail i numery telefonów, mogą być unikalne, ale mogą być później ponownie wykorzystane dla różnych osób data. Oczywiście niektóre rzeczy po prostu nie mają dobrego unikalnego identyfikatora, takiego jak nazwiska ludzi i korporacji.

Co do unikania złączeń za pomocą naturalnego klucza. Tak, może to przyspieszyć wybrane instrukcje, które nie wymagają złączeń, ale spowoduje, że miejsca, w których nadal potrzebujesz złączeń, będą wolniejsze, ponieważ złączenia int są na ogół szybsze. Prawdopodobnie spowolni również wstawianie i usuwanie oraz spowoduje problemy z wydajnością aktualizacji po zmianie klucza. Złożone zapytania (które i tak są wolniejsze) będą jeszcze wolniejsze. Proste zapytania są szybsze, ale raportowanie i złożone zapytania, a wiele działań przeciwko bazie danych może być wolniejszych. Jest to działanie równoważące, które może przechylić jedną lub drugą stronę w zależności od tego, w jaki sposób twoja baza danych jest przeszukiwana.

Dlatego nie ma jednego uniwersalnego rozwiązania. To zależy od twojej bazy danych i tego, w jaki sposób będzie ona przeszukiwana oraz jakiego rodzaju informacje są w niej przechowywane. Może być konieczne wykonanie testów, aby dowiedzieć się, co działa najlepiej w twoim środowisku.

HLGEM
źródło
1
„… Naturalne klucze często mogą ulec zmianie…” - to nie są bardzo dobre klucze! Jeśli atrybut często się zmienia, nie używaj go jako klucza (oczywiście dla różnych definicji „często”). Fabian Pascal argumentował, że istnieją cztery kryteria wyboru klucza: znajomość, nieredukowalność, stabilność i prostota. Czasami zamieniasz je na prostotę klucza zastępczego. Jak to ujął HLGEM: „Więc nie ma jednego uniwersalnego rozwiązania dla wszystkich”.
Greenstone Walker
1
@GreenstoneWalker, zgodziłbym się, że nie powinieneś wtedy wybierać go jako klucza, ale często nie masz klucza, który spełnia wszystkie cztery kryteria i musisz postępować zgodnie z tym, co jest unikalne. A gdy wyjątkowość jest kluczem copmposite, problem może być jeszcze większy pod względem wydajności, gdy musisz mieć sprzężenia.
HLGEM,
-4

Jeśli nie znasz odpowiedzi, skorzystaj z Surogatu. Oto dlaczego - jeśli przyjmowane są założenia dotyczące reguł biznesowych, a te założenia są fałszywe lub reguły się zmieniają, dane są śmieciowe. Oto przykład:

Osoba, rola, rola personalna

obecna reguła biznesowa mówi, że osoba ma jedną rolę. Tworzysz tabelę, która łączy osobę i rolę, w której PersonRole (PersonName, PersonBirthDate, PersonMotherMaidenName, ..., RoleCode)

Teraz jesteś prawdziwym purystą, jeśli chodzi o naturalne klucze! A tak na poważnie, co jeśli organizacja zdecyduje, że dana osoba może teraz pełnić wiele ról? Jakie są dalsze skutki wspierania zmiany potrzeb biznesowych?

philn5d
źródło
2
I nie masz tych problemów z kluczami zastępczymi? Pokaż, jak to zrobić.
Colin 't Hart
4
Podany przykład nie wydaje się wskazywać na nic istotnego w dyskusji.
mustaccio