Gå til innhold

SQL - Nybegynner med spørsmål


Anbefalte innlegg

Så foreign key er i detabasen som er avhengig av den andre databasen for informason.

 

Og så den constraints igjen. Hva mener du med at de vil gi navn selv? Og ikke ende opp med et autogenerert navn? Om jeg velger at BrukerID skal være primary key, vil ikke primary key hete BrukerID da?

Lenke til kommentar
Videoannonse
Annonse

Ja, det høres riktig ut.

 

 

Det er to forskjellige ting som har navn: Det feltet som inneholder IDen, og begrensningen "denne IDen må også finnes i denne andre tabellen". Feltet og begrensningen kan ha forskjellige navn - du kan ha feltet kundeID, og begrensningen fk_regning_kundeid - eller det_er_en_fordel_at_kunden_finnes.

 

En grunn til å gjøre det er at feilmeldingene du får ikke alltid vil være kjempeinformative - det kan hende du bare får navnet på begrensningen som feilet, og om du ser på det to år senere er "constraint violated: kundeID" mindre informativt enn "constraint violated: fk_regning_kundeid".

 

En annen ting er at begrensningen må ha lengre navn enn bare kolonne-navnet - se for deg at både Regning og Abonnement har en kundeID som peker til kunde.kundeID. Constraints er lagret slik at de kan "kollidere" - to kan ikke ha samme navn, selv om de hører til forskjellige tabeller, så begge kan ikke hete "kundeID".

Endret av Djn
Lenke til kommentar

Huff.. er alt dette logisk?

Så du har et navn på en kolonne. Du sier at denne skal være primary key.

Om du ikke oppgir noe annet, så vil en eventuelt feilmelding kalle kolonnen for noe helt annet.

Du må lage et navn på kolonnen + et navn som feilmeldingen skal kalle kolonnen da? Æsj..

Lenke til kommentar

La meg teste hvordan dette faktisk blir i MySQL før jeg sier noe mer ... lite øyeblikk.

 

edit:

 

I MySQL får jeg en identisk feilmelding uten navnet på keyen uansett hva jeg gjør, hvis det er en primary key. Med foreign key skjer dette:

 

Jeg har tabellene test og test2 ; test2.id1 peker til test.id . Hvis jeg prøver å sette inn noe i test2 som ikke finnes i test, får jeg:

ERROR 1452 (23000): Cannot add or update a child row: a foreign key constraint fails (`db_snapper/test2`, CONSTRAINT `fk_table2_id1` FOREIGN KEY (`id1`) REFERENCES `test` (`id`))

Som forsåvidt sier alt man trenger å vite uavhengig av hva keyen heter. Den ble forøvrig hetende test2_ibfk_1 hvis jeg ikke satte navn på den selv.

 

 

Så, tjah. Det er ikke veldig viktig. Det eneste rent praktiske jeg kan se er hvis du vil fjerne den senere, siden det krever at du skriver navnet på constrainten du vil fjerne ("alter table test2 drop foreign key fk_table2_id1") . På primary key er ikke det noe poeng, siden du uansett bare kan ha én per tabell og derfor ikke behøver å oppgi navn for å fjerne den igjen.

Endret av Djn
Lenke til kommentar

Okay da stoler jeg på det nå at det er kun en kosmetisk grunn til å bruke CONSTRAINT. For nå iværtfall :tease:

 

Hva om vi bruker 2 kolonner til å denne en key. Og vi bruker CONSTRAINT da også.

Kobler vi da sammen disse to til et felles navn? Hvordan blir det på forskjellene på feilmelding f.eks da?

Lenke til kommentar

Det er ikke kun kosmetisk, men ikke så tydelig med to tydelig adskilte entiteter som regninger og personer. Det er for å sikre dataintegriteten i databasen. Selv om applikasjonen burde håndtere dette riktig så er det databasen som i bunn og grunn har 'ansvaret' for dataene.

Lenke til kommentar

Det vil fungere likt uansett om du setter navnet selv eller om databasen plukker et for deg, ja - og det er kun hvisl du vil fjerne constrainten igjen at du trenger å vite det.

 

Jeg tror ikke du kan lage foreign key på en kombinasjon, så jeg antar du mener primary?

Constrainten "disse to tilsammen må være en lovlig primary key" vil få et (og bare ett) navn, ja. Hvis det er MySQL og primary keys du holder på med, så nevner ikke feilmeldingen navnet på constrainten uansett - så det har virkelig ingenting å si.

Lenke til kommentar

Det er ikke kun kosmetisk, men ikke så tydelig med to tydelig adskilte entiteter som regninger og personer. Det er for å sikre dataintegriteten i databasen. Selv om applikasjonen burde håndtere dette riktig så er det databasen som i bunn og grunn har 'ansvaret' for dataene.

 

Constrainten har en konkret nytte, men å sette et eget navn på den er ikke like viktig.

(Såvidt jeg har forstått snakker han om fragmentet "CONSTRAINT et_navn" i alter table-kommandoen, ikke constraints som konsept.)

Endret av Djn
Lenke til kommentar

Så foreign key er i detabasen som er avhengig av den andre databasen for informason.

 

Nei. Du har to tabeller i et skjema. Du oppretter så en foreign key constraint, også i det samme skjema, som uttrykker at den ene tabellen er avhengig av informasjon i den andre.

 

Viktig å få med seg det rette navnet på de ulike tingene, ellers blir det umulig å forstå noe som helst er jeg redd ;-)

Endret av quantum
Lenke til kommentar

Jeg skjønner ikke helt poenget uansett med dette fortsatt.

 

 

I de fleste tilfeller er det viktig at databasen er konsistent (ikke inneholder motstridende eller mangelfull informasjon), i mange tilfeller ekstremt viktig. Eksempelet med regning og person illustrerer det godt. Enhver rad i regning-tabellen MÅ være knyttet til en rad i person-tabellen. Hvis ikke blir det umulig å kreve inn pengene, eller se hvem som har betalt te pengene man er så heldig å ha fått inn på konto.

 

Et annet vikitg poeng handler om redundans, dvs. samme informasjon er lagret flere steder, og kanskje på ulike måter, i databasen. Tenk deg at person-tabellen har et felt som heter utestående_beløp. Det skal inneholde summen av alle ubetalte regninger knyttet til personen, og er opprettet for å bedre ytelsen i databasen. Men så oppdager man etter hvert at beløpet jo ikke stemmer overens med summen av alle regningene? Da vet du ikke lengre hvilket beløp som egentlig er riktig, har skyldig_beløp-feltet blitt oppdatert feil, eller har det blitt slettet regninger? Kort fortalt fins det regler for hvordan databaser skal designes for å unngå dette, og disse er delt inn i ulike nivåer kalt "normalformer". Database som oppfyller alle kravene for å være på 5. normalform vil være ganske godt strukturert, mens en som bare oppfyller kravene til 1. normalform vil være temmelig slapp i strikken.

 

En tredje viktig ting er noe som kalles transaksjoner. Det er kort fortalt en samling oppdateringer av databasen hvor man krever at alle eller ingen får lov til å gjennomføres. La oss anta du skal overføre penger fra en konto til en annen.

 

update konto sett saldo = saldo + 100 where kontonummer = 123;

update konto sett saldo = saldo -100 where kontonummer = 234;

 

Men så har vi vært smarte og laget en constraint som forhindrer at saldo blir negativ, og på konto 234 står det i utgangspunktet bare 50 kr. Da er det viktig at også innskuddet på konto 123 stanses når constraint'en på negativ saldo slår til for konto 234. Hvis begge setningene over kjører innen samme transaksjon vil databasen automatisk sørge for at det hverken trekkes fra den ene kontoen eller settes inn på den andre. Hvis setningene ikke kjører innenfor samme transaksjon vil constraint'en fortsatt hindre overtrekket, men saldoen på den andre kontoen vil like fullt bli økt med 100,-.

 

En relasjonsdatabase har veldig mye funksjonalitet som hjelper deg å ha stålkontroll på dataene dine, og kun i helt superenkle systemer er det realistisk å prøve å holde styr på slike ting selv i den konden man skriver. Når systemet blir bare litt komplekst er det så godt som fullstendig umulig å holde orden på det selv pga. omfanget av den koden man da måtte skrive for å ta høyde for alle eventualiteter.

 

Alt i alt kan det virke litt tungvint å jobbe med en database som stiller strenge krav til den informasjonen man legger inn, man må f.eks. ofte legge inn rader i mange tabeller, og i en bestemt rekkefølge. Det kan virke veldig fristende å ta snarveier for å slippe litt billigere unna, og enkelte ganger kan det forsvares å gjøre det, men det arbeidet man da sparer seg er som regel helt mikroskopisk i forhold til det arbeidet det kan være å rydde opp i inkonsistente data.

Endret av quantum
Lenke til kommentar

Opprett en konto eller logg inn for å kommentere

Du må være et medlem for å kunne skrive en kommentar

Opprett konto

Det er enkelt å melde seg inn for å starte en ny konto!

Start en konto

Logg inn

Har du allerede en konto? Logg inn her.

Logg inn nå
×
×
  • Opprett ny...