sql >> Databasteknik >  >> RDS >> Mysql

Anslagstavla - Databasoptimering

Del I

Reviderad 09 dec 10 01:00 EST

Tittade på din DDL. Ok. Vi måste ta ett steg tillbaka och organisera din databas först. Det kommer att lösa hälften av dina problem (din SQL kommer att vara enkel; och snabb; färre index; inga tillfälliga tabeller krävs). Ett tag tänkte jag, aha, du har dina kolumner, det måste vara stabilt, men det finns ingen chans. Uppifrån och ner från början, okej. Ta en titt på detta Entity Relation Diagram (det är ingen idé att arbeta med datamodellen, som är Entities, Relations och Attributes , tills vi får ER rätt), och kontrollera att det är korrekt.

  • Sättet att göra det är att svara på följande frågor (korta svar är bra). Dessa frågor förtydligar Entiteter och affärsregler . Hur du förstår databaser i allmänhet, och dina data i synnerhet, är avgörande. Du har kommit långt, på egen hand, så vi kan ta det därifrån.

  • Jag tror att ▶det här inlägget◀ stark> kan vara till hjälp för dig för att förstå de formella stadier som bör följas; som vi kortsluter här.

  • Det viktigaste, helt och hållet, glöm funktionen och eventuella kodningskrav. Data måste modelleras oberoende av applikationen, helt enkelt som Data. Funktionsmodellering är en annan vetenskap. Först skaffa en rätt; ta sedan den andra rätt; och de två tillsammans spelar vackra låtar. Försök att sätta ihop dem; gör båda uppgifterna samtidigt, och de kommer inte ens att göra ett förortsgarageband.

För korthetens skull, och för alla som läser detta, använder jag en stängd och öppen sektion; när ett öppet objekt (diskussion) är stängt kommer jag att göra det kortfattat och flytta det till avsnittet Stängt. Behåll numreringen, eftersom saker ibland kommer tillbaka för att förfölja oss. Du kanske vill göra detsamma, eller till och med ta bort diskussionen på din sida.

Länkarna till de vackra bilderna finns i slutet.

Ursäkta:redigeringen fungerar inte; undernumrering är inkonsekvent

Stängda nummer

  1. users.bb_locations_csv är en många-till-många-relation mellan användare och platser:
    • Var och en av dessa element bör vara en post i en diskret kolumn, i en diskret rad
    • En användare kan ha många platser och En plats kan ha många användare är många-till-många
    • Läs ▶det här inlägget◀ för en diskussion om hur det behandlas och i vilket skede det behandlas
    • I det här logiska stadiet, det är bara en n::n relation, som jag har ritat, du kan glömma det för tillfället, det kommer helt enkelt att levereras när vi kommer till det fysiska stadiet.
    • Tro mig, jag kommer att tillhandahålla kod som inte är mer komplex än ...WHERE IN () för ditt deklarerade ändamål.
    • Vid närmare eftertanke, om jag bryter dina fingrar kommer du att skriva ännu långsammare, så det är bäst att jag inte gör det
    • Ok, din app är webbläsarbaserad och sidan är dynamisk (mitt råd var för statiska sidor som behöver korrigeras); fortsätt med kryssrutor.
      .
  2. users.bb_categories_csv är många-till-många-relationen mellan användare och kategorier
    • Ditto.
      .
  3. Bekräftad:en bulletin (bbs) existerar inte utan en användare; en användare skickar ut en bulletin och det startar hela cykeln; bjuder sedan in svar och betyg.

    3.1 Bekräftad:Det finns egentligen bara en anslagstavla och den finns inte som en sak i databasen.

    3.2 Bekräftat:att organisationen aldrig kommer att ha mer än en anslagstavla, och klassificeringarna och kategoriseringarna hanteras alla adekvat av kategoritabellen/funktionen

  4. Raderade.

  5. Bekräftad:Skillnaden mellan bulletiner och svar är att svar är beroende av att en bulletin finns, de har ingen titel och de är inte kategoriserade efter plats eller kategori eftersom de är beroende av att själva bulletinen finns.

  6. Raderad.

  7. Kommentarer noterade. Löst.

7.1. För varje enskild bulletin som skickas av en annan användare kan varje användare skicka mer än ett svar.

7.2. För varje enskild bulletin som skickas av en användare kan den användaren skicka ett eller flera svar.

7.3. Raderad.

7.4. Raderad.

.
8. Bekräftad:varje användare kan lägga upp högst ett betyg i en bulletin (som kan återkallas/ändras)
.
9. Bekräftad:varje användare kan lägga upp högst ett betyg på ett svar (ditto)

10.1. Givet:användarnamn kommer från organisationen och är det unika namnet som identifierar anställda. Till exempel är e-postmeddelanden ldat.com@a> - autentisering görs med ldap och detta krävs för att koppla upp och hämta annan information om de anställda

  • Bekräftad:Användarnamn är en utmärkt identifierare

10.2. Bekräftad:Förnamn, Efternamn ... Födelseplats, etc finns kvar som (de traditionella) kolumner för att säkerställa People är inte duplicerade.
.
11. Givet:För närvarande kan vi identifiera våra kontor med tillfälliga namn som är allmänt kända inom organisationen, eftersom vi bara har cirka 3 huvudkontor och många fältkontor. Så exempel skulle vara Washington DC eller virginia fältkontor. Totalt tror jag att vi kommer att försöka hålla det totala antalet under 20. Jag vill också registrera den exakta adressen för varje plats eftersom det kan användas för att unikt identifiera kontor för användare.

  • Tillhandahålls:StateCode+Town som PK; IsMainOffice som booleskt.

.
12. Bekräftad:Description och Name för Category krävs.
.
13. Givet:Användare kommer inte att kunna skicka inlägg i vissa kategorier. Endast användare med tillräckligt höga rättigheter kommer att ha rätt att göra inlägg i vissa kategorier.

  • Tillhandahålls:Permission i User, Location, Category är en metod för att utvärdera sådana rättigheter.

.
14. Bekräftad:Location.Administrator är UserId av admin för Location .
.
15. Givet:Det kommer bara någonsin att finnas ett behov av att gilla eller ogilla. Jag tror inte att det behöver finnas en neutral position för detta är samma sak som att bara inte rösta? Att gilla verkar mer relevant för bulletinsvar som gör inlägg för att vara ärlig. Dvs "jag ser ditt svar och istället för att skriva mitt eget kommer jag bara hålla med dig - den befintliga anslagstavlan är något av en social aspekt i organisationen och jag tror att tycka om och ogillar/håller med och inte håller med skapar en nivå av kontroverser som uppmuntrar till deltagande . Men att gilla eller ogilla en bulletin kanske inte alltid är helt lämpligt.

15.1 Tillhandahålls:Like som booleskt i BulletinRating och ResponseRating . Detta kommer att kräva tolkning vid varje åtkomst.
15.2. När det inte längre är ett booleskt värde kan det ändras till en RatingCode , och implementerad som en uppslagstabell. Namnen bestäms sedan av Joins, och tolkningen elimineras. Jag ritade detta i den första datamodellen, så att du kunde se vad jag menade15.3. Borttagen i den andra datamodellen.
.
16. Bekräftad:varje användare har en hem Location (annat än listan över Locations som de är intresserade av).
.
17. Bekräftad:Permission enligt (13).
.
18. Bekräftad:Ytterligare behörigheter kan krävas enligt datamodellen.

18.1. Om du gör detta nu behöver du inte oroa dig för när organisationen bestämmer sig för att förhindra en viss Person från att posta Responses eller Bulletins , eller Betygsätt dem; och vill ha den funktionen implementerad igår.

18.2. Även om du inte implementerar det, lämna luckor mellan värdena du implementerar.
.
19 Bekräftad:en Bulletin handlar om en Location .

19.1. Bekräftad:Det finns inga Bulletins utan en Location

19.2. Bekräftad:Det finns inga Bulletins utan en Location .

19.3 Bekräftad:Det finns inga Bulletins utan en User (deklarativ). Men än så länge har vi inget sätt att begränsa den User; därför alla User kan infoga en Bulletin för valfri Location (du kan begränsa det i kod, t.ex. till Locations varje User Is Interested In .

19.4 Bekräftad:Det finns inga BulletinRatings utan en Bulletin och ett betyg User .

19.5 Bekräftad:Det finns inga Responses utan en Bulletin .

19.4 Bekräftad:Det finns inga ResponseRatings utan ett Responses och ett betyg User .

19.7. Men det kan finnas User , Platser, and Kategorier`, oberoende.

.
20. Om du inte har något emot det, kommer jag att tillhandahålla namnkonventioner, etc. De bör vara självförklarande, och värdet kommer bara att visas när du börjar koda SQL. Fråga gärna om något inte är det. Till att börja med är alla namn singular. Blandade skiftlägen är lättare att läsa (du ska använda versaler för SQL-språk).

20.1. Min erfarenhet är att table_name i motsats till tableName verkligen är tekniska former, och användare gillar dem inte; Genomgående blandade fall gillas av alla. Det är en av de saker som är omöjliga att ändra, så välj noga.
.
21. För ditt behov av att gruppera bord, vilket är bra, kom ihåg att det är en fysisk fråga. På nivån för logisk datamodell har tabellerna normala namn, rena av fysiska problem. Föreställ dig att de fysiska tabellerna är prefixerade med något liknande (och använd versaler för detta):
- REF_ för referens (som Användare) och uppslagstabeller
- BUL_ för Bulletin-systemet
.
Jag kan inte namnge tabeller med stora bokstäver? Jag är inte säker på varför. Jag vet inte varför jag inte kan ha tabellnamn med versaler. Har det att göra med att använda MyIsam-databastabeller?

.
22. rank (alla) kan härledas direkt från databasen (kom ihåg, oroa dig inte för koden under datamodellering). Om du lagrar det är det ett normaliseringsfel; en duplicerad kolumn; som måste hållas uppdaterad; som kan hamna ur synk med det härledda värdet; som kallas en Update Anomaly. Femte normalformen eliminerar uppdateringsavvikelser. Det är min lägsta nivå av normalisering, så det är vad du kommer att få från mig.

22.1. Jag blandar mig inte alls i sorteringsordningen eller popularitetsfrågan; i själva verket, genom ljudet av det, har du inte stängt den funktionen. Jag tar bara redundanta data, rank kolumnen , ut, som en del av normaliseringsprocessen.

22.2. Här är en ▶Snabbtutorial◀ på operatorn RANK() (som det är allmänt känt). Det är inte ANSI SQL; det är en förlängning av Oracle och MS. Det krävs dock inte om du förstår Subqueries, vilket är anledningen till att Sybase inte har det. Jag tvivlar på att MySQL har det, så du måste tänka på det. Att förstå skalära delfrågor är en förutsättning. Sybase-syntax, så slå in dina semikolon etc. Ställ gärna specifika frågor.
.
Jag har aldrig sett den metoden att skriva Rank =(SELECT... Är det så samma som (SELECT ...) som Rank?

.
22.3. Att behöva förstå varför är inga problem alls. Bara barn följer blint enkla regler, och du är verkligen inte en av dem.
.
23. Bekräftad:users.total_bulletins är överflödig; det kan härledas. Borttagen.
.
24. Alla dina PK är ID. Har du inte tröttnat på att gå vilse i koden än? Glöm att fästa Id iot PKs på allt som rör sig, låt oss ta reda på hur dina användare Identifiera deras enheter; vilka enheter är verkligt oberoende, och de andra som är beroende av oberoende enheter.

24.1. Använd aldrig Id eller någon sådan form. Om det är en PK, använd hela formuläret.

24.2. Ring location_id, location_id, var det än är, inklusive PK-tabellen. Undantaget är när du behöver visa rollen. Detta kommer att bli tydligt i datamodellen.
.
25. Du har ingen deklarativ referensintegritet, ingen definierad Främmande nycklar. Det är dåliga nyheter av många olika anledningar. När dessa frågor är klarlagda, lägg till dem. DRI betyder att så mycket som möjligt, om inte alla, integritet deklareras i SQL. ISO/IEC/ANSI SQL-standarden tillåter detta, men marknadens gratisprogram tillhandahåller inte standarden och kommer sakta ikapp. Det betyder att servern inte tillåter att en rad i FK-tabellen läggs till om inte PK finns i den överordnade tabellen. MySQL tillhandahöll nyligen DRI för främmande nycklar. För FK:er, se ▶ denna artikel◀ .

25.1. För CHECK-begränsningar och REGLER måste du implementera dessa i koden.

mina främmande nycklar är som, users-id(fk) =users.id(pk) Jag är inte säker på hur man lägger till dem annat än vad jag har gjort men kommer säkert att göra det när jag vet hur man gör.

Tjugofem. Kommentarer noterade. Jag är ingen MySQL-specialist. Ja, det är frågorna du måste ta reda på själv. I allmänhet, från min granskning, är MySQL benlös; för allt som är SQL-aktigt behöver du InnoDB.

.
27. Givet:Jag har tänkt om sorteringskraven för bulletin. Användare kan sortera kronologiskt - enkelt, är vettigt. Användare kan sortera bulletiner efter datum för det senaste svaret på bulletinen. Då kan vi glömma rang och det borde vara väldigt lätt att sortera bulletiner kronologiskt efter tidpunkten för deras senaste svar? Vad är dina tankar.

Öppna nummer

(Noll)

Datamodell

Ok, förutsatt att du inte har problem med ERD och implementerar alla stängda problem, har jag modellerat data och förberett en femte datamodell 09 dec 10 för din granskning. Jag behöver definitivt mycket mer feedback, frågor etc om detta. Jag har svårt att acceptera att det är gjort. Förmodligen bäst att börja skriva riktig kod för dina problemområden.

Länkar

▶Länk till IDEF1X Notation◀ Du måste verkligen läsa och förstå detta innan du läser Datamodellen.

▶Länk till Fifth Bulletin Data Modell◀ Enhetsrelationsdiagram finns på första sidan, följt av Datamodellen .

  • Nycklarna är ganska raka IDEF1X (förutom UserId som jag angav som en kontrapunkt); vilket betyder plånbok Relationsnycklar. Oförbättrad och inte optimerad för fysiska överväganden. Innan du gnäller på dem, lägg först märke till dem, registrera dem och utvärdera dem. Självklart kan vi lägga till Id iot-nycklar, men innan vi gör det, låt oss se till att vi förstår vad vi kommer att förlora.

  • Lägg märke till identifierarna (heldragna linjer) enligt notationsdokumentet. Ryggraden, systemets kotor är Location ... Bulletin ... Response .

  • Lägg märke till att Keys faktiskt implementerar många affärsregler.

  • Lägg märke till den naturliga hierarkin som jag har återgett. Se om det finns någon mening med det för dig.

  • VerbFraserna är verkligen viktiga; se om de betyder något.

Kommentarer angående First Data Model and Responses

En fråga jag har är att den primära nyckeln för platsen kommer att användas för att bilda den underordnade primärnyckeln? (de är förenade med en heldragen linje) Jag förstår inte riktigt det konceptet

  • Vad är en bra identifierare för Bulletin? , vad använder dina användare naturligt för att identifiera en bulletin ...
  • "har du sett bulletinen från Virginia FO igår?",
  • "Sally från Washington skriver säkert bra bulletiner", etc.

eller varför det förhållandet inte existerar mellan användaren och bulletinen?

  • Enligt avsikten ovan, eftersom jag nu har visat Rating som en tabell och vad renderingen skulle vara, kommer jag en gång att ta bort den

  • Jag tycker att Permission bör vara en Entity.

  • Bulletin PK är nu (StateCode, Town, UserId, SequenceNo) . För att vara tydlig, SequenceNo är inom StateCode, Town, UserId :det blir 5 för Sallys 5:e bulletin om MO/Billngs FO.

  • Observera att användarinställningar BulletinsPerPage ,etc, är 1::1 med User , så de finns i User; underordnad tabell skulle vara felaktig.

  • Typografiska fel korrigerade.

Kommentarer angående den andra datamodellen och svaren

  • PK:erna för båda Bulletin och Responses har ändrats för att återspegla (7). BulletinNo och ResponseNo har ersatts med BulletinDate och ResponseDate (som brukade vara CreatedDate ), för att tillåta flera svar per User enligt Bulletin .

Kommentarer om tredje datamodell och svar

Lita på att du hade en bra paus.

  1. För minst 30 år sedan (vilket jag är medveten om) hade jättarna i branschen denna debatt. Namn är alltid singular. Tabeller är substantiv. VerbFraser är verb. Detta är inte begränsat till db namnkonventioner, det gäller dokument, avhandlingar, avhandlingar, etc. Du kan ha 5 slutsatser i slutet av dokumentet, men avsnittet eller kapiteltiteln, i både innehållsförteckningen och högst upp på sidan är "Slutsats".

    Efter att ha kämpat mot dem hela vägen genom Uni, så fort jag började mitt första betalda programmeringsjobb, och såg vikten av reglerna i den verkliga världen, i motsats till de teoretiska argument vi hade på college, gav jag upp det som ett slöseri. av tid. All den tid och energi som jag slösade bort släpptes för att göra produktivt arbete. Sedan dess ifrågasätter jag inte jättarna; Jag bara accepterar. Att deras sinnen är större än mina. Det är som att acceptera normer, eller bete sig inom lagen, eller Gud. Jag har inga riktigt, riktigt bra skäl för att göra något olagligt.

    Hur som helst, det lätta att använda språk (diskussion, SQL, dokumentation) som stöds av sådana regler kan inte förklaras på ett tillfredsställande sätt; när du skriver mer och mer SQL-kod kommer det att bli tydligt.

    Du är alltid fri att använda vad du vill. Jag levererar endast singular.

  2. Bra med mig.

    Men du måste komma ihåg att dessa två element i den identifierade sekvensen (ala icke-PK Unique Index eller Alternativ Key) är universellt nödvändiga för att etablera Uniqueness för en Person. Att ta bort dem kommer att resultera i två saker. För det första kommer du inte längre att kunna identifiera unika egenskaper hos User (och därmed kan du ha dubbletter av rader). För det andra, AK blir icke-unik, en inversionsingång.

  3. Poängen är (i motsats till ett av inläggen), vilken kolumn som helst som är 1::1 med User PK, bör finnas i User . Alla preferensinställningar. Sedan vi rensat upp InterestedLocations och InterestedCategories , jag känner bara till BulletinsPerPage återstående; men jag är säker på att det finns andra. IsPreference2 är ett t.ex. av en boolesk;NumPreference3 är ett t.ex. av ett heltal. Etc. Du kan berätta för mig vad de verkliga inställningarna är.

    (Låt oss prova det i plural:... valfri kolumn som är 1::1 med Users PK, bör finnas iUsers . Det gör det bara inte för mig, jag hänger mig på den trasiga engelskan, och jag är lite värdefull när det gäller mitt modersmål.)

    Datamodellen uppdaterad.

  4. Excellent. Låt mig veta när du är bekväm med det, så ger jag dig den fysiska modellen.

    Vad sägs om verbfraserna?

Kommentarer om 06 dec 10 20:38 EST (Små uppdateringar)

.
28. Där det bara finns en förekomst av PK som FK är naturligtvis FK-kolumnnamnet detsamma som PK-kolumnnamnet. Men när det finns mer än en occ av FK (ta en titt på ResponseRating ), finns det tre UserIds ), måste vi skilja dem åt. I IDEF1X terminologi kallas detta för roller. Rollen för User vem som har utfärdat Bulletin är Issuer , och så vidare. Självklart är det bättre att använda det namnet och hålla det konsekvent i hela hierarkin (inte UserId i Bulletin och sedan när vi kommer till Response , där det finns två och en differentiering krävs, ändra den till IssuerId . Jag trodde att du kanske hade problem med det; i de tidiga stadierna är användningen Issuer.UserId så att det är helt klart att det är UserId som FK, och rollen är Issuer; när vi kommer till den fysiska modellen förenklas den till IssuerId .

Likaså har vi många DateTime-kolumner (Date förkortas om du vill; annars Dtm), som måste skiljas åt.
.
29. Var IDEF1X Notation doc inte vettigt?

  • PK för varje tabell är ovanför raden, i angiven ordning.
  • Kom ihåg att vi bär PK:erna för de överordnade tabellerna ändå, och om det finns mening, använder du dessa FK:er för att bilda den underordnade PK:n.
  • För Bulletin :

    • Platsen FK (StateCode, Town) för vilken den är utfärdad
    • UserId av Emittenten
    • och DateTime det utfärdades, för att göra det unikt.
    • därför (StateCode, Town, IssuerId, BulletinDate)`
  • För att radera alla ResponseRatings för denna Bulletin , använd WHERE = på de fyra Bulletin kolumner.

.
30. Eftersom (State, Town) är PK för Location , bära vart som helst. Och det är en del av Bulletin PK, så alla beroende tabeller bär dessa kolumner eftersom de bär Bulletin PK.

Vi hade tidigare identifierat det (State, Town) är PK, Jag lämnar det som det är Se (38) för ändring.

.
33. Värt att diskutera. Ja, om du ska visa det när du (t.ex.) visar Responses , och användarna förstår UserName . Nej, om det är 30 byte och det också finns ett unikt 4 byte UserId . Tanken är att göra dessa val medvetet, medveten om vad du ger upp, när du så småningom bestämmer dig för att någon 6 kolumn 30-byte nyckel är för besvärlig för att migrera till barnen.

  • Jag sa i början att jag skulle använda UserId som ett typiskt Id Pk, eftersom den bärs/migreras till flera underordnade tabeller.
  • Vi kan lämna hur det skapas till senare. Men det är en ren surrogat-PK.

.
34. Inga problem. Category har det redan. Jag ändrar Order till ListOrder .

.
35. Säker. Baserat på vad jag har läst och hört är jag ganska nöjd med den. Men jag skulle vilja ha mer fram och tillbaka för att få lite självförtroende, innan du skriver kod. Se det alternativt som en lärandeupplevelse och acceptera att modellen och koden kan ändras senare. Vill du att jag ska producera den fysiska nu? Om du ger mig alla rättelser kommer jag att publicera nästa version. Jag förväntar mig inställningar i User . Gå också snabbt igenom funktionerna och kontrollera att du har alla kolumner du behöver.

Titta på några av de andra svaren i syfte att lära dig och intressera dig.

.
36. Går med. Du går bara med på four tre kolumner i motsats till en. SQL är krångligt med joins, och den nya syntaxen som skulle göra det enklare är faktiskt mer krånglig. Mina kodare skriver aldrig joins:vi sparar tid och stavfel. Jag har en proc som med två eller flera tabeller genererar koden med alla kolumner och kopplingar. Jag kan inte tillräckligt mycket om MySQL för att konvertera det åt dig.

Datamodellen uppdaterad.
.

Kommentarer om 8 dec 10 20:49, fjärde datamodellen och svar

.
Kolla föregående avsnitt omedelbart ovan, det finns små uppdateringar.

IDEF1X:Din hastighet är bra.

Notera barnet alltid "ärver" den överordnade PK, som en FK (antingen heldragen eller bruten linje), annars finns det ingen relation mellan dem. Genom att använda dessa kolumner som ändå finns i barnet, för att bilda den underordnade PK, bär vi innebörden (och det är skillnaden mellan solid och trasig). Och därmed behöver vi inte leta efter en oberoende Identifierare för barnet. Relationskraften i denna metod kommer att bli tydlig senare, när du kodar.

Avsnittet vi behandlar handlar om Identifierare :naturlig vs onaturlig; meningsfullt vs meningslöst. Senare kommer du att se hur vi kan använda motorns Relationella förmåga, när den underordnade PK bildas från den överordnade PK. (Är inte ditt efternamn detsamma som din fars?)

Det är också viktigt att förstå relationsdatabaser och deras förmåga. Det går förlorat när vi närmar oss databasen (t.ex.) från ett OO-perspektiv och behandlar den som en plats för att göra våra klasser "beständiga". Därför kommer vi att försöka lära oss och använda Relationella termer. Det blir svårt när man åker till Frankrike och förväntar sig att de pratar amerikanskt, och använder samma valuta; lär dig tala 10 ord franska, och de välkomnar dig med öppna armar, och du kommer att få en helt annan upplevelse med lokalbefolkningen.

Hur som helst, fortsätt med att implementera modellen. Inse bara att vi förmodligen kommer att göra en förändring någon gång. Spara alla dina DDL. Spara alla dina testdata som insert-satser eller som en tabellbackup eller teckenformatexport (ingen aning om vad MySQL kan/inte kan göra i detta område).
37.1. Hanteras, n::n Relationen med Office &Category . Du kommer bara att "se" det när vi kommer till den fysiska modellen.

37,2. Klart.

37.3 Klart.
.
38. Excellent. Kortare också. Observera att de aldrig kommer att kunna ha två Offices i samma postnummer. NUMERIC(5,0) är bra, men jag trodde att USA gick mot 7 siffror. Det spelar ingen roll, du kan räkna ut det; det är en utmärkt PK för Office . Nu denna kolumn, som var en del av Address , förmodligen ZipCode , har upphöjts till ett högre syfte, utan duplicering; eftersom vi bär det i 5 underordnade tabeller och vi vill att PK-namnet ska vara tydligt, enligt tidigare förklarade konventioner, kommer vi att kalla det OfficeCode; OfficeZipCode kan vara dumt.

Vi behöver ett unikt index på Name för att säkerställa att de inte lägger till två Offices med samma namn. Observera att detta i förklaringssyfte faktiskt är den logiska nyckeln till Office , ersätter (StateCode, Town) , och det förblir så.

Jag tror fortfarande att du kan behöva StateCode och Town som en snabbreferens (annat än att sitta någonstans i Address )

Datamodellen uppdaterad, femte nu tillgänglig för granskning. Du angav inte dina preferenser för ...Date kontra ...Dtm . Jag går med det senare, eftersom det är mer specifikt, och identifierar också tidskomponenten. Lätt att byta.

Detta svar har nått maximal längd. Fortsättning i "Del II"



  1. Hitta alla frågor som använder en viss tabell

  2. Konfigurera och konfigurera SQL Server-replikering

  3. Undvik detta vanliga fel när du kör lagrad procedur i MS Access

  4. Är id-kolumnposition i Postgresql viktig?