數據庫范式與反范式化:如何權衡性能與數據一致性

目錄

        • 1. 什么是數據庫范式(Normalization)?
          • 第一范式(1NF)
          • 第二范式(2NF)
          • 第三范式(3NF)
        • 2. 什么是反范式化(Denormalization)?
        • 3. 反范式化的優缺點
        • 4. 反范式化的應用場景
        • 5. 范式化與反范式化結合設計
      • 總結

在數據庫設計中,范式和反范式化(Denormalization)是兩個至關重要的概念。范式化的目標是減少冗余、避免數據異常,而反范式化則側重于優化查詢性能。兩者之間的取舍,往往需要根據具體的業務需求來決定。

1. 什么是數據庫范式(Normalization)?

數據庫范式化是通過遵循一系列規則,將數據分割成多個表格,從而消除冗余和異常。它不僅可以提高數據的一致性,還可以避免插入、更新、刪除等操作中的數據異常。

第一范式(1NF)

定義:第一范式要求每列中的數據必須是原子值,不可再分。

示例
假設我們有一個學生信息表,其中包含學生所選課程的列表。

不符合1NF

CREATE TABLE Student (StudentID INT,StudentName VARCHAR(50),Courses VARCHAR(100)  -- 存儲課程列表
);

符合1NF
我們將課程拆分到單獨的表格,并確保每個值是原子性的:

CREATE TABLE Student (StudentID INT,StudentName VARCHAR(50)
);CREATE TABLE Enrollment (StudentID INT,Course VARCHAR(50),PRIMARY KEY (StudentID, Course),FOREIGN KEY (StudentID) REFERENCES Student(StudentID)
);
第二范式(2NF)

定義:第二范式要求,在滿足第一范式的基礎上,每一列都必須完全依賴于主鍵。

示例
假設一個表格中包含了學生成績和課程信息,其中某些列的依賴性不完全來自于主鍵。

不符合2NF(部分依賴)

CREATE TABLE StudentGrades (StudentID INT,Course VARCHAR(50),InstructorName VARCHAR(50),Grade CHAR(1),PRIMARY KEY (StudentID, Course)
);

符合2NF
我們將與課程相關的信息拆分成獨立的表格,消除部分依賴:

CREATE TABLE StudentGrades (StudentID INT,Course VARCHAR(50),Grade CHAR(1),PRIMARY KEY (StudentID, Course),FOREIGN KEY (StudentID) REFERENCES Student(StudentID)
);CREATE TABLE CourseInstructor (Course VARCHAR(50),InstructorName VARCHAR(50),PRIMARY KEY (Course)
);
第三范式(3NF)

定義:第三范式要求,在滿足第二范式的基礎上,每一列都必須直接依賴于主鍵,不能依賴于其他非主鍵列。

示例
在一個包含學生信息、課程及其所屬系信息的表格中,存在傳遞依賴。

不符合3NF(傳遞依賴)

CREATE TABLE StudentCourse (StudentID INT,StudentName VARCHAR(50),Course VARCHAR(50),Department VARCHAR(50),PRIMARY KEY (StudentID, Course)
);

符合3NF
我們將部門信息拆分到獨立的表格中,避免傳遞依賴:

CREATE TABLE StudentCourse (StudentID INT,Course VARCHAR(50),PRIMARY KEY (StudentID, Course),FOREIGN KEY (StudentID) REFERENCES Student(StudentID)
);CREATE TABLE Department (Course VARCHAR(50),Department VARCHAR(50),PRIMARY KEY (Course)
);
2. 什么是反范式化(Denormalization)?

反范式化是對范式化的逆操作,通常用于優化查詢性能,尤其是在讀操作頻繁的場景下。通過冗余存儲一些數據,可以減少多表連接的開銷,從而提升查詢速度。

反范式化的示例:

假設我們有兩個表格:Product(產品)和 Order(訂單),它們通過外鍵關聯。

  • 范式化后的表格
CREATE TABLE Product (ProductID INT PRIMARY KEY,ProductName VARCHAR(50),Price DECIMAL(10, 2)
);CREATE TABLE Order (OrderID INT PRIMARY KEY,ProductID INT,Quantity INT,OrderDate DATE,FOREIGN KEY (ProductID) REFERENCES Product(ProductID)
);

為了查詢一個訂單的詳細信息,我們需要進行多表連接。

  • 反范式化后的表格
    為了提高查詢效率,我們將產品的名稱和價格存儲在 Order 表中,減少了聯結操作的需求:
CREATE TABLE Order (OrderID INT PRIMARY KEY,ProductID INT,ProductName VARCHAR(50),Price DECIMAL(10, 2),Quantity INT,OrderDate DATE
);

這樣,查詢訂單時無需再聯結 Product 表,提升了查詢效率。

3. 反范式化的優缺點

優點

  • 查詢性能提升:減少了表連接,提高了查詢速度。
  • 簡化查詢:查詢更加直接和簡便。

缺點

  • 數據冗余:數據被重復存儲,可能導致存儲浪費。
  • 維護困難:如果數據發生變化(如價格調整),需要在多個表中更新,增加了維護的復雜性。
  • 更新異常:可能導致一致性問題,尤其在數據修改時。
4. 反范式化的應用場景

反范式化最適合以下場景:

  • 數據倉庫:在數據倉庫中,查詢性能比數據一致性更重要。
  • 高并發查詢:例如電商系統,查詢訂單詳情時通過反范式化減少多表連接,提升系統響應速度。
5. 范式化與反范式化結合設計

設計一個學校管理系統時,我們可以根據需求靈活結合范式化與反范式化:

  • 范式化:保證數據一致性,避免不必要的冗余。
  • 反范式化:在高查詢頻率的場景下,減少表連接,提升查詢性能。

示例
范式化設計

CREATE TABLE Student (StudentID INT PRIMARY KEY,StudentName VARCHAR(50)
);CREATE TABLE Course (CourseID INT PRIMARY KEY,CourseName VARCHAR(50)
);CREATE TABLE Teacher (TeacherID INT PRIMARY KEY,TeacherName VARCHAR(50)
);CREATE TABLE Enrollment (StudentID INT,CourseID INT,TeacherID INT,Grade VARCHAR(2),PRIMARY KEY (StudentID, CourseID),FOREIGN KEY (StudentID) REFERENCES Student(StudentID),FOREIGN KEY (CourseID) REFERENCES Course(CourseID),FOREIGN KEY (TeacherID) REFERENCES Teacher(TeacherID)
);

反范式化設計
在查詢訂單信息時,減少多表連接的需要,提升查詢效率:

CREATE TABLE Enrollment (StudentID INT,CourseID INT,TeacherID INT,CourseName VARCHAR(50),   -- 反范式化TeacherName VARCHAR(50),  -- 反范式化Grade VARCHAR(2),PRIMARY KEY (StudentID, CourseID),FOREIGN KEY (StudentID) REFERENCES Student(StudentID),FOREIGN KEY (TeacherID) REFERENCES Teacher(TeacherID)
);

總結

范式化和反范式化都是數據庫設計中必不可少的工具。范式化確保了數據的規范性和一致性,適用于數據變更頻繁且對一致性要求較高的場景;反范式化則通過犧牲一些規范性來優化查詢性能,尤其適用于查詢密集型的應用。


參考:
0voice · GitHub

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/web/62950.shtml
繁體地址,請注明出處:http://hk.pswp.cn/web/62950.shtml
英文地址,請注明出處:http://en.pswp.cn/web/62950.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

Nmap使用總結

0X00 背景 nmap是測試中常用的網絡探測工具,但是這回簡單的操作,一直了解不深入,現在深入的了解和學習一下。 在文章結構上,我把平時常用的內容提前了,以便再次查閱的時候,比較方便。 0X01 安裝 nmap可…

【記錄49】vue2 vue-office在線預覽 docx、pdf、excel文檔

vue2 在線預覽 docx、pdf、excel文檔 docx npm install vue-office/docx vue-demi0.14.6 指定版本 npm install vue-office/docx vue-demi <template><VueOfficeDocx :src"pdf" style"height: 100vh;" rendere"rendereHandler" error&…

MVC模式的理解和實踐

在軟件開發中&#xff0c;MVC&#xff08;Model-View-Controller&#xff09;模式是一種經典的設計模式&#xff0c;特別適用于構建用戶界面復雜的Web應用程序。MVC通過將應用程序的業務邏輯、數據顯示和用戶交互分離&#xff0c;使代碼結構更加清晰&#xff0c;易于維護和擴展…

[A-22]ARMv8/v9-SMMU多級頁表架構

ver0.1 [看前序文章有驚喜,關注W\X\G=Z+H=“浩瀚架構師”,可以解鎖全部文章] 前言 前文我們對SMMU的系統架構和基本功能做了簡要的介紹,現在大家大致對SMMU在基于ARM體系的系統架構下的總線位置和產品形態有了基本的了解。這里我們還是簡單做個前情回顧,從總線架構角度看…

【UE5 “RuntimeLoadFbx”插件】運行時加載FBX模型

前言 為了解決在Runtime時能夠直接根據FBX模型路徑直接加載FBX的問題&#xff0c;推薦一款名為“RuntimeLoadFBX”的插件。 用法 插件用法如下&#xff0c;只需要指定fbx的地址就可以在場景中生成Actor模型 通過指定輸入參數“Cal Collision”來設置FBX模型的碰撞 還可以通過…

(11)(3.1) ESC接地和接線注意事項

文章目錄 前言 1 歸納 2 電容式 3 電阻 前言 ESC 接地問題由 3 種形式的 ESC 信號/耦合問題組成&#xff0c;即電阻、電容和電感。在制造飛機時&#xff0c;應考慮這三個因素。 1 歸納 這是電流突然變化導致系統中出現大電壓尖峰的趨勢。電源系統中的電感主要是由 ESC 和…

精品基于Python實現的微信小程序校園導航系統-微信小程序

[含文檔PPT源碼等] [包運行成功永久免費答疑輔導] 《django微信小程序校園導航系統》該項目采用技術Python的django框架、mysql數據庫 &#xff0c;項目含有源碼、文檔、PPT、配套開發軟件、軟件安裝教程、項目發布教程、核心代碼介紹視頻等 軟件開發環境及開發工具&#xf…

Rstudio-server的安裝、配置、維護

一、安裝Rstudio-server (1)安裝R語言&#xff1a; sudo apt install r-base # 如果沒有管理員權限無法操作 # 這樣裝上R默認在/usr/bin/R其實基本上的流程都可以參考posit的官網&#xff08;也就是Rstudio的官網&#xff09;&#xff1a; https://posit.co/download/rstudio…

Python序列的應用(八):元組、字典

前言&#xff1a;在Python編程語言中&#xff0c;序列是一種非常重要的數據結構&#xff0c;它允許我們存儲和操作有序的數據集合。在前幾期的內容中&#xff0c;我們已經探討了列表&#xff08;List&#xff09;和集合&#xff08;Set&#xff09;這兩種序列的應用&#xff0c…

OpenCV 功能函數介紹

一&#xff0c; 二值化函數 功能&#xff1a; 用于對圖像進行二值化處理 參數&#xff1a; cv2.threshold(輸入你的圖像所對應的灰度圖&#xff0c; 閾值&#xff1a;是浮點還是整數取決予圖像的數據類型 最大值;高于閾值的像素值&#xff0c; 閾值類型&#xff1a;cv2.THR…

【Python】使用Selenium的find_element模塊獲取網頁上的大段文字和表格的方法(建議收藏!)

發現了一個使用Selenium的find_element模塊&#xff0c;快速獲取文字和表格的方法&#xff0c;很實在&#xff0c;以后爬網的時候&#xff0c;就不用beautifulSoup 和 pandas的read_html 混起來用了&#xff01; 文字部分&#xff1a;實現網絡節點下&#xff0c;某個節點下的其…

APP滲透測試記錄(一、Android應用基本構造)

Android應用基本構造 雷電模擬機進入 adb shell# 如果不是root權限 su一下 su 1.了解APK文件 安卓應用的擴展名為.apk(Android Application Package),它是一個包含多個文件和文件夾的數據存檔文件。 1.1 apk文件解壓后的目錄結構 AndroidManifest.xml:包含應用的大部分…

【AI知識】有監督學習之回歸任務(附線性回歸代碼及可視化)

1. 回歸的基本概念 在機器學習的有監督學習中&#xff0c;回歸&#xff08;Regression&#xff09;是一種常見的任務&#xff0c;它的目標是通過觀察數據來建立一個模型&#xff0c;用一個或多個自變量來預測因變量的值。 回歸分析通常用于&#xff1a; a.預測&#xff0c;基于…

fastadmin批量壓縮下載遠程視頻文件

后端代碼 // 批量下載并壓縮 public function downloadAll(){$ids input(ids);$row $this->model->where(id, in, $ids)->field(id,title,video_url)->select();if (!$row) {$this->error(記錄不存在);}$arr [];$tempFiles []; // 用來存儲臨時下載的視頻文…

邊緣計算+人工智能:讓設備更聰明的秘密

引言&#xff1a;日常生活中的“智能”設備 你是否發現&#xff0c;身邊的設備正變得越來越“聰明”&#xff1f; 早上醒來時&#xff0c;智能音箱已經根據你的日程播放舒緩音樂&#xff1b;走進廚房&#xff0c;智能冰箱提醒你今天的食材庫存&#xff1b;而在城市道路上&…

JVM 雙親委派模型以及垃圾回收機制

目錄 1. JVM 內存區域劃分 2. JVM 中類加載的過程 1) 類加載的基本流程 2) 雙親委派模型 3. JVM 中垃圾回收機制 1) 找到垃圾 a) 引用計數 b) 可達性分析 2) 釋放垃圾 1. JVM 內存區域劃分 一個運行起來的 Java 進程&#xff0c;其實就是一個 JVM 虛擬機。 而進程是…

ansible自動化運維(四)jinjia2模板

Jinjia2模板 前面說到playbook組成的時候&#xff0c;有介紹到template模塊&#xff0c;而template模塊對模板文件進行渲染時&#xff0c;使用的就是jinja2模板引擎&#xff0c;jinja2本身就是基于python的模板引擎&#xff0c;所以下面先來了解一下jinjia2模板的一些用法 基…

通過k-means對相似度較高的語句進行分類

本文介紹了如何使用K-Means算法對相似度較高的語句進行分類&#xff0c;并附上java案例代碼 import java.util.ArrayList; import java.util.List; import java.util.Random;public class KMeansTextClustering {public static void main(String[] args) {// 初始化語句數據集…

Oracle 19c rac 補丁升級,從19.7 to19.22-集群

1. 補丁包概述 數據庫環境 角色 數據庫 IP地址 數據庫版本 主機名 數據庫名稱 源端 RAC 172.30.21.166/167 19.7 hfcwdb66/hfcwdb67 hfdb 將以下補丁包上傳到/soft下 上傳到兩個節點的soft目錄下&#xff1a;p6880880_190000_Linux-x86-64.zip &#xff08;更新o…

Windows安裝Jira

下載 Download Jira Data Center | Atlassian https://product-downloads.atlassian.com/software/jira/downloads/atlassian-jira-software-10.3.0-x64.exe 以管理員身份安裝&#xff0c;否則彈出以下提醒 創建和配置MySQL數據庫&#xff1a;參照 Connecting Jira applicat…