爲何你精通CRUD,卻搞不懂數據庫的基本原理?

原創聲明

本文做者:黃小斜mysql

轉載請務必在文章開頭註明出處和做者。程序員

本文思惟導圖

數據庫和關係型數據庫

做爲一個程序員,不瞭解數據庫怎麼能行,那麼數據庫究竟是個啥呢,做爲一個Java工程師,平時和數據庫打交道着實很多,所謂的CRUD其實就是對數據庫進行增刪改查的操做。面試

根據百度百科的介紹,數據庫是「按照數據結構來組織、存儲和管理數據的倉庫」。是一個長期存儲在計算機內的、有組織的、有共享的、統一管理的數據集合。spring

數據庫是以必定方式儲存在一塊兒、能與多個用戶共享、具備儘量小的冗餘度、與應用程序彼此獨立的數據集合,可視爲電子化的文件櫃——存儲電子文件的處所,用戶能夠對文件中的數據進行新增、查詢、更新、刪除等操做。sql

是否是沒聽懂,好吧,簡單來講,像MySQL這樣的數據庫,就是用於存儲結構化數據的,好比一個學生的信息數據,一個商品的數據,或者是一個學生購買商品的消費數據。數據庫

聯想到平時咱們常用的Excel,其實和數據庫挺像的,數據庫其實就是一個表格,裏面有不少的數據類型,好比字符串,好比數字,再好比長文本等等。編程

而這類數據庫也叫關係型數據庫,典型表明就是MySQL。安全

再看看百度百科的介紹,關係型數據庫,是指採用了關係模型來組織數據的數據庫,其以行和列的形式存儲數據,以便於用戶理解,關係型數據庫這一系列的行和列被稱爲表,一組表組成了數據庫。用戶經過查詢來檢索數據庫中的數據,而查詢是一個用於限定數據庫中某些區域的執行代碼。關係模型能夠簡單理解爲二維表格模型,而一個關係型數據庫就是由二維表及其之間的關係組成的一個數據組織。微信

除了關係型數據庫以外,近些年來還有不少nosql(not only sql)數據庫在興起,好比MongoDB,以及圖數據庫、列式數據庫等等,這些數據庫對於新手程序員來講用的並很少,因此本文咱們只討論關於關係型數據庫的內容。網絡

關係型數據庫是咱們程序員平時用的最多,也最簡單易上手的數據庫類型,因此,學習數據庫通常也從MySQL這類關係型數據庫入手,一來它簡單好學,二來它是免費的。

個人數據庫學習歷程

我第一次據說「數據庫」這個詞仍是在大學的時候,那時候正值你們找工做,有一個同窗和咱們分享本身的求職經驗,據他所說,每一個公司都會考察你的數據庫知識,學好了數據庫,面試什麼公司都不怕。

當時我還以爲挺玄乎的,不過咱們學校確實沒來什麼大公司,我對此半信半疑,至於究竟是不是這樣,後來也就沒再追究了。

第二次接觸數據庫,是在學習Java的時候,記得當初本身跟着一個小教程,下載安裝了MySQL,而後從網上下載了demo代碼,用當時先進的開發工具eclipse跑通了別人家的代碼,其實就是增刪改查。

只不過當時對這些東西也沒啥概念,後來又下載了一個db的可視化工具,能夠更方便地瞭解本身的數據庫裏到底都有啥。

再到後來,我開始慢慢接觸項目實戰,使用數據庫的時間也愈來愈長,自覺得對於數據庫的理解還算能夠,直到我真正地接觸了數據庫相關的面試題,才讓我發現本身對於數據庫的理解是多麼的膚淺。

那個時候,我只懂寫一些簡單的crud,甚至連內外鏈接、group by和count等一些簡單的sql用法都不瞭解,除此以外,我對於數據庫的一些原理性內容幾乎也是一竅不通的,好比數據庫的索引、事務、鎖機制,我通通不知道,更別談如何回答相關的面試題了。

因而,我開始意識到學習數據庫原理是多麼重要的一件事情,我開始看數據庫方面的書籍,從最基礎的數據庫教材,再到MySQL的原理性內容,再到mybatis這類orm框架的實現,我都逐漸地開始學習和了解,直到我可以對大部分的數據庫面試題都較好地掌握。

而如今,我在一個天天要處理海量數據的公司裏工做,對於數據方面的學習已經不只僅停留在數據庫了,我還要接觸數據倉庫、分佈式數據庫以及各類大數據的應用場景,學習數據知識的道路看來短期內是走不完了。

學習數據庫,先從SQL入手

說到MySQL,就不得不談談SQL了,sql,按照百科的說法是這樣的

結構化查詢語言(Structured Query Language)簡稱SQL,是一種特殊目的的編程語言,是一種數據庫查詢和程序設計語言,用於存取數據以及查詢、更新和管理關係數據庫系統。

對於不一樣的數據庫,sql的寫法可能有一些差別,可是大體都是相同的,就拿MySQL來講,平時咱們用到最多的就是select、update、delete和insert了,這類操做統稱爲數據操縱語言DML(Data Manipulation Language),用戶經過它能夠實現對數據庫的基本操做。

固然還有操做數據庫和表的一些ddl,數據庫模式定義語言DDL(Data Definition Language),是用於描述數據庫中要存儲的現實世界實體的語言。 簡單來講,ddl其實就是用來執行建表,刪表,更改表結構等操做的

之前個人sql寫的並很少,畢竟簡單的增刪改查並不須要多複雜的sql技巧,最多就是作一下表鏈接。

再到後來,我開始作一些項目,接觸了ORM的一些框架,好比hibernate和mybatis,這些框架甚至可讓你徹底不寫sql,只要調用一些增刪改查的API便可,這讓我很長一段時間都忽略了SQL的重要性。

其實學習sql最複雜的地方並非一些高級用法,而是在於實際場景中的應用和優化。兩條sql,可能由於簡單的差別就會有很大的性能差距,差別點多是,好比有沒有走到索引,是不是全表掃描,又或者走到了哪一個索引,而這樣的性能分析只有在實際的場景裏纔有意義。

固然了,對於新手來講,學習sql的語法是放在第一位的,而後才能逐漸過渡到會使用,會優化,會分析。

關於數據庫的那些面試題

想要真正學好數據庫,搞定面試題中的相關問題,那你就必需要搞懂數據庫的基本原理。

若是你不相信,那我隨便舉幾個面試題常見的題型,好比」數據庫事務的ACID是什麼意思」、「數據庫中有哪些鎖」、「數據庫的索引用的是什麼數據結構」

上面幾道題算是簡易版的,在日常的面試中也常常可以看到,就算你只是背一背答案,可能也多少能答對一些,那麼若是再進一步,考察一下數據庫的原理性知識,恐怕就沒這麼簡單了。

舉個栗子「數據庫事務的ACID是如何實現的」,「數據庫中有哪些鎖,分別是如何實現的,如何使用」、「數據庫中的索引是如何實現的,什麼時候命中索引,什麼時候不能,爲何「

是否是感受難度一會兒就上來了。畢竟深刻到原理性的東西,懂的人就愈來愈少了。除此以外,還有不少進階的面試題,更多時候會結合實際場景來考察。

好比考察你對MySQL存儲引擎innodb的理解,對於sql優化的理解 ,以及對於分佈式場景下數據庫能力的應用,好比分佈式鎖,分佈式事務,以及分庫分表的一些問題。

知道了面試題大概都考啥以後,接下來咱們要作的就是找到癥結所在,而後一一擊破

數據庫基本原理

學習數據庫,你須要先打好基礎,數據庫原理是計算機科班的一門必修課,非科班的我選擇的是自學,我當時也是拿着那本大學教材《數據庫系統概論》來自學的。

教材這種東西,確定仍是偏理論的一點,咱們要了解的內容主要包含幾個方面

一、數據庫模型有哪些:包括層次模型、網狀模型和關係模型,咱們所用的關係型數據庫就是基於關係模型實現的。

二、關係數據庫的基礎和sql:瞭解關係數據庫的基本概念,瞭解sql的基本使用方法,至少CRUD和一些常見用法要搞懂

三、數據庫的安全性和完整性,這兩部份內容其實理論的東西比較枯燥,實際上對應到實際場景中,安全性就是要保護數據的安全,包括權限控制和數據備份,而完整性則是經過一些約定和規範來限制數據庫的存儲內容,好比咱們能夠用主鍵、惟一鍵、非空等要求來限制字段的取值。

四、關係數據理論 這部份內容頗有意思,也比較複雜,講到了數據庫的範式理論,從一範式到四範式,各有各的用法和要求,某互聯網公司「第四範式」就是用這個概念來命名的。

五、事務和鎖 最後一部份內容,就是數據庫的兩個重要組成部分,事務和鎖,事務能夠保證一組數據庫操做的ACID特性,很是適用於須要數據一致性的場景,而數據庫的鎖不可是實現事務的基礎,還能夠靈活地適用於不一樣的數據庫應用場景,咱們還能夠經過sql語句來完成加鎖和釋放,對於併發場景尤爲管用。

MySQL的實現原理

學習完了數據庫基礎以後,接下來就該學習MySQL了,畢竟不少時候咱們的數據庫應用就是MySQL。

其實MySQL裏的不少知識點和咱們上面提到的數據庫基礎大同小異,而回到MySQL的實現層,咱們就得來看看MySQL的存儲引擎了。

MySQL的存儲引擎分爲innodb和myisam,相信你們對於這兩個引擎區別的面試題看了也很多,好比innodb支持事務,支持行級鎖,而myisam不支持。

因爲如今innodb基本上是主流,因此咱們討論MySQL的時候基本上就是在討論innodb。對於MySQL的實現原理,我認爲大概有這麼一些內容須要咱們去學習。

首先,咱們瞭解MySQL裏有哪些數據類型,通常的用法如何,而後,嘗試用MySQL去跑一些sql語句,建庫建表,加索引加主鍵,總之,這些實踐能幫助你更好地學習上述內容。

想要更好地瞭解MySQL的原理,咱們就必需要了解MySQL的總體架構,通常來講,MySQL從上到下能夠分爲這麼幾層

image

客戶端

也就是咱們常常用的可視化工具,好比Navicat for MySQL

服務端

就是咱們安裝的MySQL程序,其實打開它它就是一個MySQL的服務端進程

sql執行層

sql執行層主要負責解析執行sql,裏面包含了不少複雜的組成部分,好比解釋器,分析器,優化器等等,執行層會生成一個sql的執行計劃,這個計劃也常常是咱們分析sql性能的一個重要參考內容

存儲引擎層

存儲引擎層是innodb了,好比數據要如組織和存放,索引要如何創建和管理等等,加鎖怎麼加,事務如何實現,都是這一層要考慮的內容。

文件系統層

存儲引擎的下一層就是文件系統了,數據庫的數據如何和文件系統進行交互,就是這一層要作的事情了。

索引

不得不說,索引絕對是數據庫中最常常考察,考點也最多的內容了。

好比給你一條sql,那麼它可否命中索引,能命中哪些索引,若是想要命中某個索引,你應該如何修改,這種問題面試時是否是常常看到,變來變去這麼多題型,其實面試官就是想考察你對於索引的理解。

還有就是,索引的數據結構,同樣是很是熱門的考點之一,索引實際上是基於B+樹來實現的,不知道b+樹是啥,請回去看數據結構。

簡單來講,它是一種多路搜索樹,致力於更短的時間來完成數據檢索,由於它的高度比二叉樹要低,而比起普通的b樹,它的非葉節點只起索引做用,而葉子節點是順序串聯的,因此很是適合作搜索樹。

若是你理解了這一點,那麼面對此類面試題就能夠更加從容一些,面試官其實就是想知道你對b+樹的瞭解到了什麼樣的程度而已。

事務和鎖

除了索引以外,數據庫中最複雜的內容可能就是事務和鎖了。

就拿事務的ACID特性來講,你須要瞭解每一個大寫字母背後的實現原理,好比原子性是如何實現的,一致性是如何保證的,背後的原理是什麼。

咱們平時經常使用的事務可能就是spring裏的事務模板,在事務裏執行的同庫數據庫操做,要麼都成功,要麼都失敗,這就是原子性。

兩個事務之間互不影響,這就是隔離性,固然了,這裏又涉及到了事務隔離級別。

事務隔離級別包括讀未提交,讀已提交,可重複讀和序列化,每一個事務隔離級別都適用於某種數據庫讀寫場景,不少時候,咱們都須要搞懂隔離級別背後的原理,才能更好地適用它。

MySQL裏默認使用可重複讀的隔離級別,這個級別基本上能夠保證咱們的事務按照預期執行,在MySQL中,這個事務隔離級別甚至能夠解決幻讀的問題。

在MySQL的事務背後,其實有一個隱藏的boss,那就是數據庫的鎖,不少事務的隔離級別都是經過鎖來實現的,好比可重複讀只要加行鎖就能夠實現了,而幻讀則須要加上間隙鎖next-key lock來實現。

行級鎖和表級鎖是MySQL中的兩種鎖,表級鎖顧名思義,會直接鎖表,一次只有一個事務可以訪問,而行級鎖其實鎖的也並不是是一行,在MySQL中,這個鎖加在索引上,而這個索引對應的數據每每不止一行,因此這個行級鎖只是理論意義上的"行級鎖"

說了這麼多,要理解MySQL的事務和鎖,仍是要多看看相關的書籍和文章,理解其內部的實現原理,知其然也要知其因此然。

下面又到了咱們熟悉的資源推薦環節

推薦資源

書籍

數據庫

0 《數據庫系統概論》

數據庫原理應該是教材吧,這本書做爲數據庫入門來講仍是能夠的,畢竟不是專門作DB的,看大厚書用處不大,這本書把數據庫的基本概念都講完了。

1 sql必知必會

​​

這本書主要是講解sql語句怎麼寫,畢竟數據庫最重要的一點就是要熟練地使用sql語句,固然這本書也能夠當作工具書來使用。

2 深刻淺出MySQL

​​

這本書適合做爲MySQL的學習書籍,當你有了必定的MySQL使用經驗後,能夠看看它,該書從數據庫的基礎、開發、優化、管理維護和架構5個方面對MySQL進行了詳細的介紹,講的不算特別深,可是足夠咱們使用了。這本書我也只看了一部分。

3 MySQL技術內幕:innodb存儲引擎

​​

看完上面那本書之後,對MySQL算是比較熟悉了,不過對於面試中常考的innodb引擎,仍是推薦一下這本書把,專門講解了innodb存儲引擎的相關內容。我尚未細看,可是內容足夠你學好innodb了。

4 高性能Mysql

​​

這本書能夠說是很厚了,更適合DBA拜讀,講的太詳細了,打擾了。

微信公衆號【程序員黃小斜】

致力於讓自學編程這件事變得更簡單,授人以魚也要授人以漁。做者自學編程轉行互聯網,目前是阿里巴巴Java工程師,專一於分享程序員前沿技術乾貨和編程學習心得,期待你的關注,和咱們一塊兒進步! 

文中所提到的電子書均可以避免費領取,在個人公衆號後臺回覆「計算機網絡」便可領取對應的下載地址。

相關文章
相關標籤/搜索