寬表和窄表的區別

2021-09-11 16:47:24 字數 1374 閱讀 2565

寬表和窄表的建設該如何選擇?

這個問題相信糾結了很多從是資料庫開發、資料倉儲開發和後台開發人員;單單考慮這個問題,難給出乙個絕對的答案;本人從事資料倉儲開發工作到現在已經有一年半時間了,對於這個問題,我也曾經糾結過,但是是否有絕對的答案呢?事實上任何東西都沒有絕對的說法。

考慮這樣的乙個問題,乙個公司有這樣的乙個需求:

設計銷售領域的訂單事實表,該事實表應該包含哪些維度和度量?事實表和維錶該分別如何去設計?

好了,我們把關鍵資訊拿出來,首先我們要有維度包括:銷售員、銷售員所屬部門、下訂單的時間;度量:銷售量;

那麼,訂單事實表,其實就是乙個商品銷售的清單;

依照這個思路,我們建立的第乙個模型可能是以下這樣的:

單單看上去,貌似是符合我們的問題的需要,而且符合資料庫的正規化設計:沒有冗餘字段;但是情況真的就是這樣嗎?

答案是否定的,確實對於一般的oltp系統而言這樣的表設計確實減少了冗餘和,增刪改查等操作也很方便,但是往往對於我們的統計系統、olap、資料探勘而言,情況卻並非如此,舉個例子:我們要統計每個部門各自的銷售量為多少?那麼對於上表,sql是這樣的:

select a.*,b.sid into #dep_saleser from department a,saleser_dim b on a.dep_id = b.dep_id;

select count(1),a.dep_name from #dep_saleser a,order_fact b on a.sid=b.sid group by a.dep_name;

對於這麼乙個簡單的需求已經要寫兩了sql去實現了,其實資料庫表模型的的設計是靈活的,我們完全可以根據我們的業務去設計我們的資料表;考慮到部門和銷售員可以是同屬於銷售者這個維度,只是他們是有上下級別關係的那麼依照這個思路,我們的模型可以建立為下面這樣:

那麼統計每個部門各自的銷售量,可以用如下sql去實現:

select count(1),a.dep_name from saleser_dim a,order_fact b

on a.sid=b.sid group by a.dep_name;

確實對於這個模型而言,有些情況下會出現冗餘(填寫使用者,沒有填寫部門;填寫部門沒填寫使用者);但是對於提取數統計的邏輯又相對來說要簡單了好多;

考慮到要實現取數簡單,我們還可以想出另外一種方法:

看上去好像不錯哦~~,取資料也就一句sql就搞掂了,但是卻是最最槽糕的情況,有可能乙個銷售員,前幾天登記的部門是a,但是其實他的所屬於的部門為b,那麼對於上面這個模型,我們得改動銷售員和訂單表;而對於上面的其他兩個模型都僅僅需要改動一張表就行了,造成查詢資料部一致往往也就是這種資料模型所造成的。

所謂的寬表就是字段比較多的表,包含的維度層次比較多,造成冗餘也比較多,毀正規化設計,但是利於取數統計,而窄表往往對於oltp比較合適,符合正規化設計原則;

寬表和窄表的區別

一 寬表 1 寬表 從字面意義上講就是字段比較多的資料庫表。通常是指業務主題相關的指標 維度 屬性關聯在一起的一張資料庫表。由於把不同的內容都放在同一張表儲存,寬表已經不符合三正規化的模型設計規範,隨之帶來的主要壞處就是資料的大量冗餘,與之相對應的好處就是查詢效能的提高與便捷。這種寬表的設計廣泛應用...

寬依賴和窄依賴 Spark 寬依賴和窄依賴

1.前言 上一節spark dag概述 spark中rdd的高效與dag圖有著莫大的關係,在dag排程中需要對計算過程劃分stage,暴力的理解就是stage的劃分是按照有沒有涉及到shuffle來劃分的,沒涉及的shuffle的都劃分在乙個stage裡面,這種劃分依據就是rdd之間的依賴關係。針對...

將MySQL的窄表轉換成寬表的方法

在擴充套件設計中,使用窄表可以很方便的增加新的項。如果用寬表,就會需要修改表結構,很不方便。而使用寬表在查詢過濾資料的時候會比窄表方便很多,資料的記錄量也會少很多。這裡介紹一種將窄表轉置成寬表的語法 select userkey,max case tagid when 1 then valueid ...