Domanda

Per quanto ne so, le chiavi esterne (FK) vengono utilizzate per aiutare il programmatore a manipolare i dati nel modo corretto.Supponiamo che un programmatore lo stia già facendo nel modo giusto, allora abbiamo davvero bisogno del concetto di chiavi esterne?

Esistono altri usi per le chiavi esterne?Mi sto perdendo qualcosa qui?

È stato utile?

Soluzione

Le chiavi esterne aiutano a rafforzare l'integrità referenziale a livello di dati.Inoltre migliorano le prestazioni perché normalmente sono indicizzati per impostazione predefinita.

Altri suggerimenti

Le chiavi esterne possono anche aiutare il programmatore a scrivere meno codice utilizzando cose come ON DELETE CASCADE.Ciò significa che se hai una tabella contenente utenti e un'altra contenente ordini o qualcosa del genere, l'eliminazione di un utente potrebbe eliminare automaticamente tutti gli ordini che puntano a quell'utente.

Non riesco a immaginare di progettare un database senza chiavi esterne.Senza di essi, alla fine sei destinato a commettere un errore e a corrompere l'integrità dei tuoi dati.

Non sono necessario, in senso stretto, ma i vantaggi sono enormi.

Ne sono abbastanza certo FogBugz non ha vincoli di chiave esterna nel database.Sarei interessato a sapere come funziona il Software Fog Creek il team struttura il proprio codice per garantire che non introducano mai incoerenze.

Uno schema di database senza vincoli FK è come guidare senza cintura di sicurezza.

Un giorno te ne pentirai.Non dedicare quel po' di tempo extra agli aspetti fondamentali della progettazione e all'integrità dei dati è un modo sicuro per evitare grattacapi in seguito.

Accetteresti un codice così sciatto nella tua applicazione?Ciò accedeva direttamente agli oggetti membro e modificava direttamente le strutture dati.

Perché pensi che questo sia stato reso difficile e addirittura inaccettabile nelle lingue moderne?

SÌ.

  1. Ti mantengono onesto
  2. Mantengono onesti i nuovi sviluppatori
  3. Tu puoi fare ON DELETE CASCADE
  4. Ti aiutano a generare simpatici diagrammi che spiegano da soli i collegamenti tra le tabelle

Personalmente sono favorevole alle chiavi esterne perché formalizza la relazione tra le tabelle.Mi rendo conto che la tua domanda presuppone che il programmatore non stia introducendo dati che violerebbero l'integrità referenziale, ma ho visto troppi casi in cui l'integrità referenziale dei dati viene violata, nonostante le migliori intenzioni!

Vincoli di chiave pre-estranea (noti anche come integrità referenziale dichiarativa o DRI) è stato dedicato molto tempo all'implementazione di queste relazioni utilizzando i trigger.Il fatto che possiamo formalizzare la relazione mediante un vincolo dichiarativo è molto potente.

@John - Altri database possono creare automaticamente indici per chiavi esterne, ma SQL Server no.In SQL Server, le relazioni di chiave esterna sono solo vincoli.È necessario definire separatamente il proprio indice sulle chiavi esterne (il che può essere utile).

Modificare:Vorrei aggiungere che, secondo me, l'uso di chiavi esterne a supporto di ON DELETE o ON UPDATE CASCADE non è necessariamente una buona cosa.In pratica, ho scoperto che la cascata di eliminazione dovrebbe essere attentamente considerata in base alla relazione dei dati, ad es.hai un genitore-figlio naturale in cui questo potrebbe essere OK o la tabella correlata è un insieme di valori di ricerca.L'utilizzo degli aggiornamenti a cascata implica che si sta consentendo la modifica della chiave primaria di una tabella.In tal caso, ho un disaccordo filosofico generale sul fatto che la chiave primaria di una tabella non dovrebbe cambiare.Le chiavi dovrebbero essere intrinsecamente costanti.

Supponiamo che un programmatore lo stia già facendo nel modo giusto

Fare una simile supposizione mi sembra una pessima idea;in generale il software è straordinariamente difettoso.

E questo è il punto, davvero.Gli sviluppatori non riescono a sistemare le cose, quindi garantire che il database non possa essere riempito con dati errati è una buona cosa.

Sebbene in un mondo ideale, i join naturali utilizzerebbero le relazioni (ad es.Vincoli FK) anziché corrispondere ai nomi delle colonne.Ciò renderebbe gli FK ancora più utili.

Senza una chiave esterna come si fa a sapere che due record in tabelle diverse sono correlati?

Penso che ciò a cui ti riferisci sia l'integrità referenziale, in cui non è consentito creare il record figlio senza un record genitore esistente, ecc.Questi sono spesso conosciuti come vincoli di chiave esterna, ma non devono essere confusi con l'esistenza di chiavi esterne.

C'è un vantaggio nel non avere chiavi esterne?A meno che tu non stia utilizzando un database scadente, gli FK non sono così difficili da configurare.Allora perché dovresti adottare una politica per evitarli?Una cosa è avere una convenzione di denominazione che dice che una colonna fa riferimento a un'altra, un'altra è sapere che il database sta effettivamente verificando quella relazione per te.

Suppongo che tu stia parlando di vincoli di chiave esterna imposti dal database.Probabilmente stai già utilizzando chiavi esterne, semplicemente non ne hai parlato al database.

Supponiamo che un programmatore stia già facendo questo nel modo giusto, quindi abbiamo davvero bisogno del concetto di chiavi straniere?

Teoricamente no.Tuttavia, non è mai esistito un software privo di bug.

I bug nel codice dell'applicazione in genere non sono così pericolosi: identifichi il bug e lo risolvi, dopodiché l'applicazione funziona di nuovo senza problemi.Ma se un bug consente a dati corrotti di entrare nel database, allora sei bloccato!È molto difficile ripristinare i dati corrotti nel database.

Considera se si è verificato un bug sottile FogBugz ha consentito la scrittura di una chiave esterna corrotta nel database.Potrebbe essere semplice correggere il bug e inviare rapidamente la correzione ai clienti in una versione di correzione del bug.Tuttavia, come dovrebbero essere riparati i dati corrotti presenti in decine di database? Corretto il codice potrebbe ora rompersi improvvisamente perché i presupposti sull'integrità delle chiavi esterne non sono più validi.

Nelle applicazioni web in genere c'è solo un programma che comunica con il database, quindi c'è solo un posto dove i bug possono corrompere i dati.In un'applicazione aziendale potrebbero esserci diverse applicazioni indipendenti che comunicano con lo stesso database (per non parlare delle persone che lavorano direttamente con la shell del database).Non c'è modo di essere sicuri che tutte le applicazioni seguano gli stessi presupposti senza bug, sempre e per sempre.

Se i vincoli sono codificati nel database, la cosa peggiore che può succedere con i bug è che all'utente venga mostrato un brutto messaggio di errore su alcuni SQL vincolo non soddisfatto.Questo è tanto È preferibile piuttosto che lasciare che dati corrotti entrino nel database aziendale, dove a loro volta danneggeranno tutte le applicazioni o porteranno semplicemente a tutti i tipi di output errati o fuorvianti.

Oh, e anche i vincoli di chiave esterna migliorano le prestazioni perché sono indicizzati per impostazione predefinita.Non riesco a pensare ad alcun motivo non utilizzare vincoli di chiave esterna.

Gli FK sono molto importanti e dovrebbero sempre esistere nel tuo schema, a meno che tu non sia eBay.

Penso una cosa sola ad un certo punto deve essere responsabile di garantire relazioni valide.

Per esempio, Rubino sui binari non utilizza chiavi esterne, ma convalida autonomamente tutte le relazioni.Se accedi al tuo database solo da quell'applicazione Ruby on Rails, va bene.

Tuttavia, se sono presenti altri client che scrivono nel database, senza chiavi esterne devono implementare la propria convalida.Quindi hai due copie del codice di convalida che molto probabilmente sono diverse, cosa che qualsiasi programmatore dovrebbe essere in grado di dire è un peccato capitale.

A quel punto le chiavi esterne sono davvero necessarie, poiché consentono di spostare nuovamente la responsabilità su un unico punto.

Le chiavi esterne consentono a qualcuno che non ha mai visto il tuo database di determinare la relazione tra le tabelle.

Potrebbe andare tutto bene ora, ma pensa a cosa succederà quando il tuo programmatore se ne andrà e qualcun altro dovrà subentrare.

Le chiavi esterne consentiranno loro di comprendere la struttura del database senza dover trascinare migliaia di righe di codice.

Per quanto ne so, le chiavi esterne vengono utilizzate per aiutare il programmatore a manipolare i dati nel modo corretto.

Gli FK consentono al DBA di proteggere l'integrità dei dati dagli errori degli utenti quando il programmatore non riesce per farlo, e talvolta per proteggersi dagli errori dei programmatori.

Supponiamo che un programmatore lo stia già facendo nel modo giusto, allora abbiamo davvero bisogno del concetto di chiavi esterne?

I programmatori sono mortali e fallibili.Gli FK lo sono dichiarativo il che li rende più difficili da rovinare.

Esistono altri usi per le chiavi esterne?Mi sto perdendo qualcosa qui?

Sebbene non sia questo il motivo per cui sono stati creati, gli FK forniscono suggerimenti forti e affidabili agli strumenti di creazione di diagrammi e ai costruttori di query.Questo viene trasmesso agli utenti finali, che hanno un disperato bisogno di suggerimenti forti e affidabili.

Non sono strettamente necessarie, così come non sono strettamente necessarie le cinture di sicurezza.Ma possono davvero salvarti dal fare qualcosa di stupido che incasina il tuo database.

È molto più bello eseguire il debug di un errore di vincolo FK piuttosto che dover ricostruire un'eliminazione che ha danneggiato l'applicazione.

Sono importanti perché la tua applicazione non è l'unico modo in cui i dati possono essere manipolati nel database.La tua applicazione può gestire l'integrità referenziale nel modo onesto che vuole, ma tutto ciò che serve è un idiota con i giusti privilegi che si presenti ed emetta un comando di inserimento, eliminazione o aggiornamento a livello di database e tutta l'applicazione dell'integrità referenziale dell'applicazione viene aggirata.Inserire i vincoli FK a livello di database significa che, salvo che questo idiota scelga di disabilitare il vincolo FK prima di emettere il comando, il vincolo FK causerà il fallimento di un'istruzione di inserimento/aggiornamento/eliminazione errata con una violazione dell'integrità referenziale.

Ci penso in termini di costi/benefici...In MySQL, l'aggiunta di un vincolo è una singola riga aggiuntiva di DDL.Sono solo una manciata di parole chiave e un paio di secondi di riflessione.Questo è l'unico "costo" secondo me...

Gli strumenti adorano le chiavi esterne.Le chiavi esterne impediscono dati errati (ovvero righe orfane) che potrebbero non influire sulla logica o sulla funzionalità aziendale e quindi passare inosservati e accumularsi.Impedisce inoltre agli sviluppatori che non hanno familiarità con lo schema di implementare intere parti di lavoro senza rendersi conto che manca una relazione.Forse tutto è fantastico nell'ambito della tua attuale applicazione, ma se ti sei perso qualcosa e un giorno viene aggiunto qualcosa di inaspettato (pensa ai report fantasiosi), potresti trovarti in un punto in cui devi ripulire manualmente i dati errati che si sono accumulati sin dall'inizio dello schema senza un controllo imposto dal database.

Il poco tempo necessario per codificare ciò che è già nella tua testa mentre metti insieme le cose potrebbe risparmiare a te o a qualcun altro un sacco di dolore mesi o anni lungo la strada.

La domanda:

Ci sono altri usi per le chiavi straniere?Mi sto perdendo qualcosa qui?

E' un po' carico.Inserisci commenti, rientri o nomi di variabili al posto di "chiavi esterne"...Se hai già capito perfettamente la cosa in questione, per te "non ti serve".

Riduzione dell'entropia.Ridurre la possibilità che si verifichino scenari caotici nel database.Abbiamo difficoltà perché dobbiamo considerare tutte le possibilità, quindi, secondo me, la riduzione dell’entropia è la chiave per il mantenimento di qualsiasi sistema.

Quando facciamo un'ipotesi, ad esempio:ogni ordine ha un cliente da cui il presupposto dovrebbe essere applicato qualcosa.Nei database quel "qualcosa" sono le chiavi esterne.

Penso che questo valga il compromesso in termini di velocità di sviluppo.Certo, puoi programmare più velocemente senza di loro e questo è probabilmente il motivo per cui alcune persone non li usano.Personalmente ho trascorso diverse ore con Hibernate e qualche vincolo di chiave esterna che si arrabbia quando eseguo qualche operazione.TUTTAVIA, so qual è il problema, quindi è meno problematico.Sto utilizzando strumenti normali e ci sono risorse che mi aiutano a risolvere questo problema, forse anche persone che possono aiutarmi!

L'alternativa è consentire a un bug di insinuarsi nel sistema (e dato abbastanza tempo, lo farà) dove una chiave esterna non è impostata e i tuoi dati diventano incoerenti.Quindi, ricevi una segnalazione di bug insolito, indaga e "OH".Il database è fregato.Ora quanto tempo ci vorrà per sistemare la cosa?

Puoi vedere le chiavi esterne come un vincolo che,

  • Aiuta a mantenere l'integrità dei dati
  • Mostrare come i dati sono correlati tra loro (il che può aiutare a far rispettare la logica e le regole aziendali)
  • Se utilizzato correttamente, può aiutare ad aumentare l'efficienza con cui i dati vengono recuperati dalle tabelle.

Al momento non utilizziamo chiavi esterne.E per la maggior parte non ce ne pentiamo.

Detto questo, probabilmente inizieremo a usarli molto di più nel prossimo futuro per diversi motivi, entrambi per ragioni simili:

  1. Diagramma.È molto più semplice produrre un diagramma di un database se vengono utilizzate correttamente le relazioni di chiave esterna.

  2. Supporto per strumenti.È molto più semplice creare modelli di dati utilizzando Visual Studio 2008 per cui può essere utilizzato LINQ to SQL se ci sono relazioni di chiave esterna corrette.

Quindi immagino che il punto sia che abbiamo scoperto che se stiamo facendo molto lavoro SQL manuale (costruisci query, esegui query, blahblahblah) le chiavi esterne non sono necessariamente essenziali.Una volta che inizi a utilizzare gli strumenti, però, diventano molto più utili.

La cosa migliore dei vincoli di chiave esterna (e dei vincoli in generale, in realtà) è che puoi fare affidamento su di essi quando scrivi le tue query.Molte query possono diventare molto più complicate se non si può fare affidamento sul fatto che il modello dati sia "vero".

Nel codice, generalmente riceviamo semplicemente un'eccezione lanciata da qualche parte, ma dentro SQL, generalmente otterremo solo le risposte "sbagliate".

In teoria, Server SQL potrebbe utilizzare i vincoli come parte di un piano di query, ma ad eccezione dei vincoli di controllo per il partizionamento, non posso dire di averlo mai visto.

Le chiavi esterne non erano mai state esplicite (tabella RIFERIMENTI CHIAVE ESTERA (colonna)) dichiarate nei progetti (applicazioni aziendali e siti Web di social network) su cui ho lavorato.

Ma c'è sempre stata una sorta di convenzione nel nominare le colonne che erano chiavi esterne.

È come con normalizzazione del database - devi sapere cosa stai facendo e quali sono le conseguenze di ciò (principalmente prestazioni).

Sono a conoscenza dei vantaggi delle chiavi esterne (integrità dei dati, indice per la colonna di chiave esterna, strumenti consapevoli dello schema del database), ma ho anche paura di utilizzare le chiavi esterne come regola generale.

Inoltre diversi motori di database potrebbero servire le chiavi esterne in modo diverso, il che potrebbe portare a sottili bug durante la migrazione.

La rimozione di tutti gli ordini e le fatture del cliente eliminato con ON DELETE CASCADE è l'esempio perfetto di uno schema di database dall'aspetto gradevole, ma progettato in modo errato.

SÌ.ON DELETE [RESTRICT|CASCADE] impedisce agli sviluppatori di bloccare i dati, mantenendoli puliti.Recentemente mi sono unito a un team di sviluppatori Rails che non si concentravano sui vincoli del database come le chiavi esterne.

Per fortuna ho trovato questi: http://www.redhillonrails.org/foreign_key_associations.html -- I plug-in RedHill on Ruby on Rails generano chiavi esterne utilizzando il file convenzione sulla configurazione stile.Una migrazione con Codice prodotto creerà una chiave esterna per il file id nel prodotti tavolo.

Dai un'occhiata agli altri fantastici plug-in su Collina Rossa, comprese le migrazioni racchiuse in transazioni.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top