說實話我也是前兩周才知道有資料庫重構這回事,當時聽說這個概念的時候,唯一的反應就是:資料庫居然也能重構?剛好上周去圖書館借書,看見了《資料庫重構》這本書,就借回來看了幾章。下面會結合自己的體會介紹一些這本書的一些觀點。
<b>資料庫重構概念</b><b></b>
資料庫重構是對資料庫schema進行的簡單改動,在保持行為和資訊語義的前提下改進設計。
資料庫重構可以重構資料庫schema的結構:比如表、視圖的定義、修改; 重構資料庫的功能:如存儲過程、觸發器等。
<b>資料庫重構的困難</b><b></b>
資料庫重構其實并不像代碼重構那麼簡單,對資料庫結構的改動,真的是牽一發而動全身。可能你要改動業務邏輯層、ui表示層、甚至是牽連到一些其它模
塊、外部調用程式,還有像資料庫裡面的函數、存儲過程、觸發器等、光是把這些牽扯的例舉出來,都會讓你頭皮發麻,還要大量的測試;而且對一個已經上線的系
統,你有這個魄力去重構嗎?就算你有,未必其它同僚、尤其拍闆的人(經理)也未必同意,這裡面的風險太大,代價太大了…..其實這都是因為資料庫重構比代
碼重構難,複雜。下面是我自己概括的一些:
代碼重構隻需要保持行為語義,
而資料庫重構還要保持資訊語義。
資料庫架構所導緻的耦合度(資料庫與外部程式是高度耦合的),資料庫重構變得相當複雜。按情況分分為單應用資料庫、多應用資料庫(相對複雜得
多),下面是我按書上圖畫的單應用資料庫和多應用資料庫。

資料庫重構缺少工具支援。像代碼重構,很多ide(內建開發環境)都已經提供了代碼重構功能,比如vs裡面菜單欄裡面有重構選項,許多人都經常使用。但是資料庫到現在為止沒啥工具支撐。相信資料庫工具提供商以後也一定會增添這些功能的。
資料庫設計、開發采用傳統的、串行式的思維過程,基本上忽略了靈活的方式(說實話,我對作者這個觀點不太了解)。我的了解資料庫開發一直采用傳統的模組化,設計,然後編碼實作,沒有采用反映現代方法學(如xp 和rup)的演進式方式。
不是每個開發者對系統各部分、資料庫架構都十分了解,不是每個人都精通資料庫和應用程式開發。也就是說可能某人隻精通資料庫、而不精通c#開發,
那麼重構就顯得比較困難。還有很多人隻了解系統的部分結構,而不了解整體,這對資料庫重構影響很大,作者建議結對程式設計,dba和架構師(技術人員)結對進
行資料庫重構
<b>資料庫重構的分類</b><b></b>
結構重構:
對一個或多個表或試圖做一些變更。比如将一列從一個表移到另外一個表,将多用途的列拆分為一些單獨的列。每個列用于單一用途。
資料品質重構:一種變更,改進了資料庫中所包含資訊的品質。例如,不允許列為空,確定它總是有值,或對一列采用統一格式,確定一緻性。
參照完整性重構:一種變更,它確定參照的行在另外一個表的存在,并確定不需要的行被相應地删除。增加觸發器支援兩個實體間的層疊式删除。
架構重構。
一種變更,它從整體上改變了外部程式與資料庫進行互動的方式。用存儲過程取代部分代碼和腳本。
方法重構:
對方法(存儲過程、函數、觸發器)的一種變更,改進方法品質,比如存儲過程改名,把存儲過程裡面的*用相應的字段替換、、、、、
替換:
這不屬于重構,轉換時對資料schema的一個變更,它改變了schema的語義。
<b>資料庫味道</b><b></b>
正如flower在重構裡面說的代碼的壞味道一樣,作者也嘗試總結了一些資料庫的壞味道。
多用途的列。 如果一個列被用于多種用途,就有可能存在額外的代碼來確定資料以“正确的方式”使用。個人認為像表裡面用來判别性别、是否删除的字段這樣的多用途列還不是壞味道,如果超出了兩個應用,就應該考慮重構了。
多用途的表。 如果一個表用來存放多種不同資料來源的資料。
重複的資料。重複的資料對操作型資料庫來說是一種嚴重的問題,因為資料存放在幾個地方,不一緻的機會就增加了。個人認為适當的備援還是必須的。這個隻能試情況而論。
列太多的表。一個表包含太多的列時,說明表缺乏内聚——它試圖存放來自幾類實體的資料。我見過一個表幾十個字段的設計,隻能用“無語”來形容我的感受。
行太多的表。大的表就有性能問題,查找就十分耗時,你這時就需要對表進行垂直分割:将一些列移到另外一個表,将一些行移到另外一個表,進行水準分割。
“智能”列:智能列是這樣一種列,其中資料的不同位置代表了不同的概念。這個我不太了解(沒有這方面的使用經驗),作者的建議進行更小粒度的分割字段。
害怕變化。如果你害怕改變你的資料庫schema,因為你擔心更改會破壞其它很多應用程式,那麼這就是一個明确的信号。
<b>資料庫重構在開發中的位置</b><b></b>
作者提到了大多數面向資料技術本質上都是串行的。諸如邏輯資料模組化或實體資料模組化。希望資料庫dba采用類似開發者使用的現代演進式技術來開發,并
能從中獲益。作者提供了一幅圖關于在一些關鍵開發活動中的高層視圖,這些活動發生在涉及對象和關系資料庫的現代項目中。請注意,所有的箭頭都是雙向的。你
需要在這些活動之間來回疊代。同時注意沒有定義起點和終點——顯然這不是傳統的串行式過程。