視圖、索引介紹

目錄

1、視圖

1.1、什么是視圖

1.2、創建視圖

1.3、使用視圖

1.4、修改視圖

1.5、刪除視圖

1.6、視圖的優點

2、MySQL存儲結構

2.1、MySQL中的頁

3、索引

3.1、索引的數據結構

3.2、B樹 和 B+樹

3.3、B+樹在MySQL索引中的應用

3.4、索引分類


1、視圖

1.1、什么是視圖

視圖是一個虛擬的表,它是基于一個或多個基礎表或基他視圖的查詢的結查集

視圖本身不存儲數據,而是通過執行查詢來動態生成數據

案例:查詢用戶的所有信息和考試成績

所有有這樣開發需求的程序員,都需要寫這么復雜的SQL

把以上SQL定義成一個視圖,用戶就可以像操作普通表一樣使用視圖進行查詢、更新和管理。

1.2、創建視圖

語法:create view?view_name [(column_list)] as?select_statement

1. 不指定列名創建

由于定義視圖時沒有指定列名,這時視圖中的列是由結果集決定的

為重復的列起別名就可以解決列重復的問題

2.?指定列名創建視圖

指定列名之后,視圖會根據指定的列名創建,查詢結果集中是否重名不重要

創建完成后,可以使用指定列名排序

select * from v_student_score_v1 order by id;

1.3、使用視圖

-- 查看視圖
show tables;
-- 查詢視圖

show create view v_student_score;
-- 使用視圖

select * from v_student_score;

使用真實表,在查詢列表中隨時可以加上其他字段,而使用視圖查詢,只能查到創建時指定的字段,不能再添加查詢字段,所以可以使用視圖隱藏不能被展示的字段

視圖和真實表進行表連接查詢:

select * from v_student_total_points v, student s where v.id = s.id;

1.4、修改視圖

通過基本表修改數據,會影響視圖

// 修改唐三藏的JAVA成績為99分

?update score set score = 99 where student_id = 1 and course_id = 1;

// 查詢視圖,發現唐三藏這條記錄已被修改

select * from v_student_socre;

通過視圖修改數據,也會影響基本表

// 修改唐三藏的計算機?絡成績為99分

update v_student_socre set score = 99 where score_id = 3;

// 發現更新失敗,因為創建視圖時使用了order by 語句


//?更新視圖

update v_student_socre_v1 set score = 99 where score_id = 3;

// 查看基礎表數據發現已被修改

select * from score where student_id = 1 and course_id = 5;

結論:不論更新了視圖還是基礎表,相互都會被影響,查詢的數據都是最新結果

以下視圖不可更新:
? 創建視圖時使用聚合函數的視圖
? 創建視圖時使用 DISTINCT
? 創建視圖時使用 GROUP BY 以及 HAVING 子句
? 創建視圖時使用 UNION 或 UNION ALL
? 查詢列表中使用子查詢
? 在FROM子句中引用不可更新視圖

1.5、刪除視圖

語法:drop view 視圖名;

1.6、視圖的優點

1. 簡單性:視圖可以將復雜的查詢封裝成一個簡單的查詢。例如,針對一個復雜的多表連接查詢,可以創建一個視圖,用戶只需查詢視圖而無需了解底層的復雜邏輯。

2. 安全性:通過視圖,可以隱藏表中的敏感數據。例如,一個系統的用戶表中,可以創建一個不包含密碼列視圖,普通用戶只能訪問這個視圖,而不能訪問原始表。

3. 邏輯數據獨立性:視圖提供了一種邏輯數據獨立性,即使底層表結構發生變化,只需修改視圖定義,而無需修改依賴視圖的應用程序。使用到應用程序與數據庫的解耦

4. 重命名列:視圖允許用戶重命名列名,以增強數據可讀性。

2、MySQL存儲結構

2.1、MySQL中的頁

1..ibd文件中最重要的結構體就是Page(頁),頁是內存與磁盤交互的最小單元,默認大小為16KB每次內存與磁盤的交互至少讀取一頁,所以在磁盤中每個頁內部的地址都是連續的,之所以這樣做,是因為在使用數據的過程中,根據局部性原理,將來要使用的數據大概率與當前訪問的數據在空間上是臨近的,所以一次從磁盤中讀取一頁的數據放入內存中,當下次查詢的數據還在這個頁中時就可以從內存中直接讀取,從而減少磁盤I/O提高性能

.ibd 文件:innodb存儲引擎生成的表空間文件,后綴是.ibd


局部性原理:
時間局部性(Temporal Locality):如果?個信息項正在被訪問,那么在近期它很可能還會被再次訪問。
空間局部性(Spatial Locality):將來要?到的信息?概率與正在使?的信息在空間地址上是臨近的。

2.?每一個頁中即使沒有數據也會使用 16KB 的存儲空間,同時與索引的B+樹中的節點對應

查看頁大小:show variables like 'innodb_page_size';

3.?在MySQL中有多種不同類型的頁,最常用的就是用來存儲數據和索引的"索引頁",也叫做"數據頁",但不論哪種類型的頁都會包含頁頭(File Header)和頁尾(File Trailer),頁的主體信息使用數據"行"進行填充,數據頁的基本結構如下圖所示:?

3、索引

MySQL的索引是?種數據結構,它可以幫助數據庫高效地查詢、更新數據表中的數據。索引通過 ?定的規則排列數據表中的記錄,使得對表的查詢可以通過對索引的搜索來加快速度。 類似于書籍的目錄,通過指向數據行的位置,可以快速定位和訪問表中的數據

使用索引的目的只有一個,就是提升數據檢索的效率,在應用程序的運行過程中,查詢操作的頻率遠遠高于增刪改的頻率。

3.1、索引的數據結構

hash

時間復雜度是0(1),查詢速度非常快,但是MySQL并沒有選擇HASH做為索引的默認數據結構主要原因是 HASH 不支持范圍查找

二叉搜索樹

中序遍歷是一個有序序列,所以支持范圍查找,但有幾個問題導致它不適合用作索引的數據結構

1. 最壞情況下時間復雜度為O(N)
2. 節點個數過多無法保證樹高

  • AVL和紅黑樹,雖然是平衡或者近似平衡,但是畢竟是二叉結構,當節點個數過多時,無法保證樹的高度
  • 在檢索數據時,每次訪問某個節點的子節點時都會發生一次磁盤IO,而在整個數據庫系統中,IO是制約數據庫性能的主要因素,減少IO次數可以有效的提升性能

N叉樹

每個節點可以有超過兩個的子節點,可以解決樹高的問題

時間復雜度:O(logN)
在數據量相同的情況下,可以有效的控制樹高,也就是說可以使用更少的IO次數找到目標節點,從而提高數據庫的效率。但是MySQL認為N叉樹做為索引的數據結構還不夠好

3.2、B樹 和 B+樹

B樹 和 B+樹都是 N 叉搜索樹

B樹:上述N叉樹的案例就是B樹

B+樹:

B+樹是?種經常用于數據庫和文件系統等場合的平衡查找樹,是MySQL索引采用的數據結構

時間復雜度:O(logN)
可以有效的控制樹高

B+樹的特點:

1. 一個節點,可以存儲N個key,N個key劃分出了N個區間(而不是N+1個區間)
2. 每個節點中的key的值,都會在子節點中也存在(同時該key是子節點的最大值)
3. B+樹的葉子節點,是首尾相連,類似于一個鏈表

4. 非葉子節點只保存索引,不存數據,真實數據都保存在葉子節點中

面試題:

1.?索引使用了什么數據結構?

答:B+樹

2. 介紹一下B+樹

答:B+樹與B樹對比,B+樹的優勢是:
1. 葉子節點之間有一個相互連接的引用,可以通過一個葉子節點找到它相鄰的兄弟節點
MySQL索引在組織葉子節點時使用的是雙向鏈表
2. 非葉子節點的值都包含在葉子節點中
MySQL索引 非葉子節點只保存了對子節點的引用,沒有保存真實的數據,所有真實的數據都保存在葉子節點中
3. 對于B+樹而言,在相同樹高的情況下,查找任一元素的時間復雜度都一樣,性能均衡

3.3、B+樹在MySQL索引中的應用

以查找id為5的記錄,完整的檢索過程如下:
1. 首先判斷B+樹的根節點中的索引記錄,此時5<7,應訪問左孩子節點,找到索引頁2
2. 在索引頁2中判斷id的大小,找到與5相等的記錄,命中,加載對應的數據頁

以上的IO過程,加載索引頁1-->加載索引頁2-->加載數據頁3(3次IO)


所有關于頁的操作和訪問都是在內存中進行的

理論上三層樹高的B+樹可以存放多少條記錄:

假設一條用戶數據大小為1KB,在忽略數據頁中數據頁自身屬性空間占用的情況下,一頁可以存16條數據
索引頁一條數據的大小為,主鍵用BIGINT類型占8Byte,下一頁地址6Byte,一共是14Byte,一個索引頁可以保存16*1024/14=1170條索引記錄
如果只有三層樹高的情況,綜合只保存索引的根節點和二級節點的索引頁以及保存真實數據的數據頁,那么一共可以保存1170*1170*16=21,902,400條記錄,也就是說在兩千多萬條數據的表中,可以通過三次IO就完成數據的檢索

3.4、索引分類

主鍵索引

1. 當在一個表上定義一個主鍵PRIMARY KEY時,會自動創建索引,索引的值是主鍵列的值。InnoDB使用它作為聚集索引 / 聚簇索引 / 主鍵索引。

2. 推薦為每個表定義一個主鍵。如果沒有邏輯上唯一且非空的列或列集可以使用主鍵,則添加一個自增列。

3.?如果沒有為表定義PRIMARY KEY,InnoDB使用第一個UNIQUE和NOT NULL的列作為聚集索引。(聚集索引可以標識數據行的唯一性)

普通索引

1.?最基本的索引類型,沒有唯一性的限制。工作中通常為查詢頻繁的列創建索引為了提升查詢效率

2.?可以包含一個列也可以包含多個列,包含多個列時稱為復合索引或組合索引

唯一索引

1.?當在一個表上定義一個唯一鍵 UNQUE 時,自動創建唯一索引。

2.?與普通索引類似,但區別在于唯一索引的列不允許有重復值。

如果表中沒有 PRIMARY KEY 或合適的 UNIQUE索引,InnoDB 會為新插入的行生成一個行號并用 6 字節的 ROW_ID 字段(數據行中的一個隱藏列之一)記錄,ROW_ID 單調遞增,并使用ROW_ID做為索引。這種索引也是聚集索引

非聚集索引

1. 聚集索引以外的索引稱為非聚集索引或二級索引

2.?二級索引中的每條記錄都包含該行的主鍵列,以及二級索引指定的列。

3.?InnoDB使用這個主鍵值來搜索聚集索引中的行,這個過程稱為回表查詢

注意

1.?創建索引之后都會生成一棵索引樹,創建多少索引生多少棵索引樹

2. 創建索引后,生成的索引樹,也是會占用磁盤空間的創建索引時,要慎重考慮一下需不需要
3. 索引樹越多,對增、刪,改的效率影響越大

非聚集索引的查詢過程:
1. 通過索引查到葉子節點中的索引記錄
2. 通過索引記錄中的主鍵值,去主鍵索引樹中找相應的完整記錄,這個過程稱為回表查詢

select * from student where name = '張三';(回表查詢

3.?通過索引查詢的列,包含在索引中,不需要回表查詢了,這種的現象叫做索引覆蓋

假設 name 和 sn 這兩列為組合索引:

select sn from student where name = '張三';(索引覆蓋

^

問題:當前的組合索引中通過學號來查姓名索引生不生效(走不走索引)?

select name from student where sn = '100002';

答:不生效。創建索引時,name列在sn列之前,那么使用的時候也要先使用name再使用sn如果只使用sn列,那么索引就會失效,如果非要使用sn列查,可以為sn單獨創建一個索引。

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

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

相關文章

QT6(46)5.2 QStringListModel 和 QListView :列表的模型與視圖的界面搭建與源代碼實現

&#xff08;154&#xff09;理論講解 &#xff1a; 例題程序的界面搭建 &#xff1a; &#xff08;155&#xff09;以下開始完善代碼 &#xff0c;先準備要給 model 的源數據&#xff0c;一些字符串 &#xff1a; 給出該頭文件&#xff0c;以全面展示其內容&#xff1a; #i…

C++設計模式(GOF-23)——03 C++觀察者模式(Observer / Event、發布-訂閱模式、事件模式)

文章目錄 一、觀察者模式概述二、傳統代碼 vs 觀察者模式對比1. 傳統實現&#xff08;緊耦合&#xff09;2. 觀察者模式實現&#xff08;松耦合&#xff09; 三、Mermaid 類圖說明四、核心設計要點1. 接口分層設計2. 通知機制實現3. 擴展性驗證 五、應用場景與注意事項適用場景…

海外 AI 部署:中國出海企業如何選擇穩定、安全的云 GPU 基礎設施?

2025年&#xff0c;中國 AI 企業在模型訓練、產品落地和創新應用上不斷刷新人們的認知。DeepSeek-R1、Qwen3 等國產大模型密集亮相&#xff0c;國內大模型產業熱潮持續升溫。與此同時&#xff0c;一個現實的問題也在被越來越多企業關注&#xff1a;模型雖然訓練得起&#xff0c…

AI繪畫工具實測:Stable Diffusion本地部署指

對于想要深度體驗AI繪畫的創作者來說&#xff0c;本地部署Stable Diffusion能帶來更自由的創作空間。本文將詳細介紹Windows系統下的部署流程&#xff0c;幫助你在個人電腦上搭建專業的AI繪畫環境。 硬件準備與基礎環境配置 部署前需確認電腦配置&#xff1a;建議NVIDIA顯卡&…

macOS - 快速上手使用 YOLO

文章目錄 一、關于 yolo二、安裝三、命令行使用官方示例yolo cfgyolo predict 四、Python 調用results 數據 一、關于 yolo YOLO(YOLO&#xff08;You Only Look Once&#xff09;是一種流行的物體檢測和圖像分割模型&#xff0c;由華盛頓大學的約瑟夫-雷德蒙&#xff08;Jose…

<script setup> 語法糖

下面&#xff0c;我們來系統的梳理關于 Vue 3 <script setup> 語法糖 的基本知識點&#xff1a; 一、<script setup> 核心概念 1.1 什么是 <script setup>&#xff1f; <script setup> 是 Vue 3 中 Composition API 的編譯時語法糖&#xff0c;它通過…

MYSQL-InnoDB邏輯存儲結構 詳解

InnoDB邏輯存儲結構 段—區—頁—行 表空間&#xff1a; 默認情況下InnoDB有一個共享表空間ibdata1&#xff0c;所有數據放入這個表空間&#xff0c;如果開啟了innodb_file_per_table&#xff08;默認ON&#xff09;&#xff0c;每張表都可以放到一個單獨的表空間&#xff0…

[特殊字符] Python 批量合并 Word 表格中重復單元格教程(收貨記錄案例實戰)

在日常辦公中&#xff0c;Word 表格中常出現重復的“供應商名稱”或“物料編碼”&#xff0c;會導致表格冗余且視覺混亂。這時候&#xff0c;用 Python 自動合并重復單元格可以大幅提升表格專業度和可讀性。本篇給大家演示如何用 python-docx 實現該功能。 ? 功能概覽 自動讀取…

從零構建Node.js服務托管前端項目

下面是一個完整的指南&#xff0c;教你如何從零開始構建一個Node.js服務來托管前端項目&#xff0c;并代理API請求到其他服務器。 1. 項目初始化 # 創建項目目錄 mkdir node-proxy-server cd node-proxy-server# 初始化npm項目 npm init -y# 安裝必要依賴 npm install expres…

Lynx vs React Native vs Flutter 全面對比:三大跨端框架實測分析

一文看懂三大熱門跨端技術的歷史淵源、架構機制、開發體驗、包體積對比與性能評估。 我陪你用實測數據帶你理性選型&#xff0c;不踩坑&#xff0c;不盲信。 1. 框架簡介&#xff1a;它們是誰&#xff1f;來自哪里&#xff1f;干嘛用&#xff1f; 框架名稱所屬公司發布時間初衷…

CKESC的ROCK 180A-H 無人機電調:100V 高壓冗余設計與安全保護解析

一、核心技術參數與性能指標 電壓范圍&#xff1a;支持 12~26S 鋰電&#xff08;適配 110V 高壓系統&#xff09;電流特性&#xff1a; 持續工作電流&#xff1a;90A&#xff08;特定散熱條件&#xff09;瞬時耐流&#xff08;1 秒&#xff09;&#xff1a;220A&#xff0c;3 …

優化 ArcPy 腳本性能

使用并行處理 如果硬件條件允許&#xff0c;可以使用 Python 的并行處理模塊&#xff08;如 multiprocessing&#xff09;來同時處理多個小任務。這樣可以充分利用多核處理器的優勢&#xff0c;提高腳本的執行效率。 import multiprocessing def process_raster(raster):arcpy…

Windows下CMake通過鴻蒙SDK交叉編譯三方庫

前言 華為鴻蒙官方的文章CMake構建工程配置HarmonyOS編譯工具鏈 中介紹了在Linux平臺下如何使用CMake來配置鴻蒙的交叉編譯環境&#xff0c;編譯輸出在Harmony中使用的第三方so庫以及測試demo。 本文主要是在Windows下實現同樣的操作。由于平臺差異的原因&#xff0c;有些細節…

從C學C++(6)——構造函數和析構函數

從C學C(6)——構造函數和析構函數 若無特殊說明&#xff0c;本博客所執行的C標準均為C11. 構造函數與析構函數 構造函數定義 構造函數是特殊的成員函數&#xff0c;當創建類類型的新對象&#xff0c;系統自動會調用構造函數構造函數是為了保證對象的每個數據成員都被正確初…

清理 Windows C 盤該注意什么

C 盤空間不足會嚴重影響系統性能。 清理 C 盤文件時&#xff0c;首要原則是安全。錯誤地刪除系統文件會導致 Windows 無法啟動。下面我將按照 從最安全、最推薦到需要謹慎操作的順序&#xff0c;為你詳細列出可以清理的文件和文件夾&#xff0c;并提供操作方法。 第一梯隊&…

Python Selenium 滾動到特定元素

文章目錄 Python Selenium 滾動到特定元素?? **1. 使用 scrollIntoView() 方法&#xff08;最推薦&#xff09;**&#x1f5b1;? **2. 結合 ActionChains 移動鼠標&#xff08;模擬用戶行為&#xff09;**&#x1f9e9; **3. 使用坐標計算滾動&#xff08;精確控制像素&…

你寫的 Express 接口 404,可能是被“動態路由”吃掉了

本文首發在我的個人博客&#xff1a;你寫的 Express 接口 404&#xff0c;可能是被“動態路由”吃掉了 前情提要 最近參與公司的一個項目前端 React&#xff0c;后端用的 Express。目前我就做一些功能的新增或者修改。 對于 Express &#xff0c;本人沒有公司項目實戰經驗&…

【Java面試】你是怎么控制緩存的更新?

&#x1f504; 一、數據實時同步失效&#xff08;強一致性&#xff09; 原理&#xff1a;數據庫變更后立即失效或更新緩存&#xff0c;保證數據強一致。 實現方式&#xff1a; Cache Aside&#xff08;旁路緩存&#xff09;&#xff1a; 讀流程&#xff1a;讀緩存 → 未命中則…

react-嵌套路由 二級路由

什么是嵌套路由&#xff1f; 在一級路由中又內嵌了其他路由&#xff0c;這種關系就叫做嵌套路由&#xff0c;嵌套至一級路由內的路由又稱作二級路由 嵌套路由配置 實現步驟 配置二級路由 children嵌套 import Login from "../page/Login/index"; import Home from …

【CMake基礎入門教程】第八課:構建并導出可復用的 CMake 庫(支持 find_package() 查找)

很好&#xff01;我們進入 第八課&#xff1a;構建并導出可復用的 CMake 庫&#xff08;支持 find_package() 查找&#xff09;。 &#x1f3af; 本課目標 你將掌握&#xff1a; 如何構建一個庫并通過 install() 導出其配置&#xff1b; 如何讓別人在項目中使用 find_package…