2009-01-06 70 views
5

對於數據庫分配,我必須建立一個學校系統的模型。部分要求是爲員工,學生和家長建立信息模型。在數據庫中建模繼承

在UML類圖中,我將此模型化爲這三個類是人類類型的子類型。這是因爲他們都需要關於地址數據等信息。

我的問題是:我如何在數據庫(mysql)中建模?

思想至今如下:

  1. 創建包含每個類型的所有信息單片人表,將有很多依賴於被存儲什麼類型的空值。 (我懷疑這對講師來說會很好,除非我令人信服地辯解)。
  2. 有三個外鍵的人表引用了子類型,但其中兩個將是空的 - 實際上我甚至不確定這是否合理或可能?
  3. 根據這一wikipage about django這是可以實現的亞型的主鍵如下:

    "id" integer NOT NULL PRIMARY KEY REFERENCES "supertype" ("id")
  4. 別的東西,我還沒有想過...

因此,對於那些誰擁有在數據庫之前模擬繼承;你是怎麼做到的?你推薦什麼方法?爲什麼?

鏈接到文章/博客文章或以前的問題是值得歡迎的。

謝謝你的時間!

UPDATE

好的謝謝你的回答。我已經有一個單獨的地址表,所以這不是一個問題。

乾杯,

亞當

+0

如果這是一個家庭作業添加作業標籤請 – JoshBerke 2009-01-06 17:15:02

+0

還檢查了:http://stackoverflow.com/questions/5802/inheritance-in-database – JoshBerke 2009-01-06 17:15:55

回答

5

4臺的工作人員,學生,家長和個人爲通用的東西。 工作人員,學生和家長都有外鍵的鑰匙,每個鑰匙都會引用回人(而不是其他方式)。

人員具有標識此人的子類別(即員工,學生或家長)的字段。

編輯:

正如HLGM指出,地址應該存在於一個單獨的表,因爲任何人可能有多個地址。 (但是 - 我即將不同意自己的意見 - 你可能希望故意將地址約束爲每人一個,限制郵件列表的選擇等)。

1

「因此,對於那些誰已經在數據庫之前建模繼承;?你是怎麼做到這一點你推薦什麼方法,爲什麼 」

方法1和3都不錯。差異主要在於你的用例是什麼。

1)適應性 - 哪個更容易改變? FK關係與父表的幾個單獨的表。

2)性能 - 哪些需要更少的連接?一張桌子。

大鼠。沒有設計完成這兩個。

此外,除了您的單表和FK對父母之外,還有第三種設計。

三個獨立的表格,包含一些常用列(通常在所有子類表中複製並粘貼超類列)。這非常靈活且易於使用。但是,它需要三個表格的聯合來組裝整個列表。

2

嗯,我認爲所有的方法都是有效的,任何講師因爲個人意見而在一張桌子上甩掉它(除非要求具體說你不應該這樣做)正在消除一個可行的策略。

我強烈建議您查閱關於NHibernate的文檔,因爲這提供了執行上述的不同方法。我現在會嘗試鸚鵡很差。

您的選擇:

  • 1)與所有具有 「分隔符」 列中的數據一個表。本專欄陳述了這個人是什麼樣的人。這在簡單的情況下是可行的,並且(嚴重)高性能,因爲連接會傷害太多
  • 2)每個類將導致列重複,但會避免重新連接,所以它的簡單和快速在大多數情況下,lil和索引緩解了這一點)。
  • 3)「適當的」繼承。規範化的版本。你幾乎在那裏,但你的鑰匙是在錯誤的地方國際海事組織。你的員工表應包含一個PERSONID所以你可以再做:

    選擇employee.id,從員工內部person.name加入上employee.personId = PERSON.PERSONID

人要獲得所有的名字只在人員表上指定姓名的員工。

0

OO數據庫通過相同的東西,並拿出幾乎相同的選項。

如果要在數據庫中建立子類的模型,您可能已經考慮過我在真正的OO數據庫中看到的解決方案(將字段留空)。

如果不是,您可能會考慮創建一個不以這種方式使用繼承的系統。

繼承應該總是相當謹慎地使用,這可能是一個非常糟糕的情況。

一個很好的指導方針是永遠不要使用繼承,除非你實際上擁有的代碼對「父」類的字段做的事情不同於「兒童」類中的相同字段。如果您的類中的業務代碼沒有專門引用某個字段,那麼該字段絕對不應該導致繼承。

但是,如果你在學校,這可能不符合他們想教的東西......

2

我會去#3。

您的目標是打動演講者,而不是PM或客戶。學者傾向於不喜歡空值,並可能(潛意識地)懲罰你使用其他方法(依賴於空值)。

而且你不一定需要django擴展名(PRIMARY KEY ... REFERENCES ...)可以使用普通的FOREIGN KEY。

0

「正確」的答案賦值的目的大概是3:

Person 
PersonId Name Address1 Address2 City Country 

Student 
PersonId StudentId GPA Year .. 

Staff 
PersonId StaffId Salary .. 

Parent 
PersonId ParentId ParentType EmergencyContactNumber .. 

哪裏PERSONID永遠是首要的關鍵,也是最後三個表的外鍵。

我喜歡這種方法,因爲它可以很容易地代表具有多個角色的同一個人。例如,老師也可以成爲父母。

0

我建議五個表 人 學生 員工 家長 地址

爲什麼 - 因爲人們可以有多個addesses,人們也可以擁有多個角色,並且希望爲員工的信息是比信息不同的你需要爲家長或學生存儲。

此外,您可能希望將名稱存儲爲last_name,Middle_name,first_name,Name_suffix(如jr。),而不是名稱。相信我你會想要在last_name上搜索!名稱不是唯一的,所以你需要確保你有一個獨特的代理主鍵。

請在嘗試設計數據庫之前閱讀有關規範化的內容。這裏是開始與源: http://www.deeptraining.com/litwin/dbdesign/FundamentalsOfRelationalDatabaseDesign.aspx

0

超級型的人應該這樣被創建:

CREATE TABLE Person(PersonID int primary key, Name varchar ... etc ...) 

全部子類型應該這樣創建:

CREATE TABLE IF NOT EXISTS Staffs(StaffId INT NOT NULL , 
    PRIMARY KEY (StaffId) , 
    CONSTRAINT FK_StaffId FOREIGN KEY (StaffId) REFERENCES Person(PersonId) 
) 

CREATE TABLE IF NOT EXISTS Students(StudentId INT NOT NULL , 
    PRIMARY KEY (StudentId) , 
    CONSTRAINT FK_StudentId FOREIGN KEY (StudentId) REFERENCES Person(PersonId) 
) 

CREATE TABLE IF NOT EXISTS Parents(PersonID INT NOT NULL , 
    PRIMARY KEY (PersonID) , 
    CONSTRAINT FK_PersonID FOREIGN KEY (PersonID) REFERENCES Person(PersonId) 
) 

在亞型員工,學生,家長的外鍵中增加了兩個條件:

  1. 人員行不能刪除,除非相應的子類型行將不會刪除 。對於例如如果學生 表中有一個學生條目參照Person表,則不刪除學生條目 不能刪除人員條目,這是非常重要的。如果學生 對象被創建,則不刪除學生對象,我們不能 刪除基礎Person對象。

  1. 所有基本類型有外鍵「非空」,以確保每個基地 類型將有現有總是基本類型。對於例如如果您創建 學生對象,則必須先創建Person對象。