關於NoSQL與SQL的區別

關於NoSQL與SQL的區別
首先將和大家聊聊為什麼NoSQL會在關係型資料庫已經非常普及的情況下異軍突起?
隨著網際網路的不斷發展,各種類型的應用層出不窮,所以導致在這個雲計算的時代,對技術提出了更多的需求,主要體現在下面這四個方面:
1.、低延遲的讀寫速度:應用快速地反應能極大地提升用戶的滿意度;
2、支撐海量的數據和流量:對於搜索這樣大型應用而言,需要利用PB級別的數據和能應對百萬級的流量;
3、大規模集群的管理:系統管理員希望分布式應用能更簡單的部署和管理;
龐大運營成本的考量:IT經理們希望在硬體成本、軟體成本和人力成本能夠有大幅度地降低;
目前世界上主流的存儲系統大部分還是採用了關係型資料庫,其主要有一下優點:
1、事務處理—保持數據的一致性;
2、由於以標準化為前提,數據更新的開銷很小(相同的欄位基本上只有一處);
3、可以進行Join等複雜查詢。
雖然關係型資料庫已經在業界的數據存儲方面占據不可動搖的地位,但是由於其天生的幾個限制,使其很難滿足上面這幾個需求:
1、擴展困難:由於存在類似Join這樣多表查詢機制,使得資料庫在擴展方面很艱難;
2、讀寫慢:這種情況主要發生在數據量達到一定規模時由於關係型資料庫的系統邏輯非常複雜,使得其非常容易發生死鎖等的並發問題,所以導致其讀寫速度下滑非常嚴重;
3、成本高:企業級資料庫的License價格很驚人,並且隨著系統的規模,而不斷上升;
4、有限的支撐容量:現有關係型解決方案還無法支撐Google這樣海量的數據存儲;
業界為了解決上面提到的幾個需求,推出了多款新類型的資料庫,並且由於它們在設計上和傳統的NoSQL資料庫相比有很大的不同,所以被統稱為「NoSQL」系列資料庫。總的來說,在設計上,它們非常關注對數據高並發地讀寫和對海量數據的存儲等,與關係型資料庫相比,它們在架構和數據模型方量面做了「減法」,而在擴展和並發等方面做了「加法」。現在主流的NoSQL資料庫有BigTable、HBase、Cassandra、SimpleDB、CouchDB、MongoDB和Redis等。接下來,將關注NoSQL資料庫到底存在哪些優缺點。

在優勢方面,主要體現在下面這三點:
1、簡單的擴展:典型例子是Cassandra,由於其架構是類似於經典的P2P,所以能通過輕鬆地添加新的節點來擴展這個集群;
2、快速的讀寫:主要例子有Redis,由於其邏輯簡單,而且純內存操作,使得其性能非常出色,單節點每秒可以處理超過10萬次讀寫操作;
3、低廉的成本:這是大多數分布式資料庫共有的特點,因為主要都是開源軟體,沒有昂貴的License成本;
但瑕不掩瑜,NoSQL資料庫還存在著很多的不足,常見主要有下面這幾個:
1、不提供對SQL的支持:如果不支持SQL這樣的工業標準,將會對用戶產生一定的學習和應用遷移成本;
2、支持的特性不夠豐富:現有產品所提供的功能都比較有限,大多數NoSQL資料庫都不支持事務,也不像MS SQL Server和Oracle那樣能提供各種附加功能,比如BI和報表等;
3、現有產品的不夠成熟:大多數產品都還處於初創期,和關係型資料庫幾十年的完善不可同日而語;

上面NoSQL產品的優缺點都是些比較共通的,在實際情況下,每個產品都會根據自己所遵從的數據模型和CAP理念而有所不同,接下來,將給大家介紹NoSQL兩個最重要的概念:數據模型和CAP理念,並在本文最後,對主流的NoSQL資料庫進行分類。
NoSQL並不是關係型資料庫管理系統,本文將會介紹NoSQL資料庫與關係型資料庫之間的差別,同時還會討論在何種場景下應該使用NoSQL,何種場景下不應該使用。由於NoSQL還是個相對較新的技術,因此它還面臨著很多挑戰。
時至今日,網際網路上有數以億計的用戶。大數據與雲計算已經成為很多主要的網際網路應用都在使用或是準備使用的技術,這是因為網際網路用戶每天都在不斷增長,數據也變得越來越複雜,而且有很多非結構化的數據存在,這是很難通過傳統的關係型資料庫管理系統來處理的。NoSQL技術則能比較好地解決這個問題,它主要用於非結構化的大數據與雲計算上。從這個角度來看,NoSQL是一種全新的資料庫思維方式。
為何要使用NoSQL資料庫?
1、NoSQL具有靈活的數據模型,可以處理非結構化/半結構化的大數據
現在,我們可以通過Facebook、D&B等第三方輕鬆獲得與訪問數據,如個人用戶信息、地理位置數據、社交圖譜、用戶產生的內容、機器日誌數據以及傳感器生成的數據等。對這些數據的使用正在快速改變著通信、購物、廣告、娛樂以及關係管理的特質。沒有使用這些數據的應用很快就會被用戶所遺忘。開發者希望使用非常靈活的資料庫,能夠輕鬆容納新的數據類型,並且不會被第三方數據提供商內容結構的變化所累。很多新數據都是非結構化或是半結構化的,因此開發者還需要能夠高效存儲這種數據的資料庫。但遺憾的是,關係型資料庫所使用的定義嚴格、基於模式的方式是無法快速容納新的數據類型的,對於非結構化或是半結構化的數據更是無能為力。NoSQL提供的數據模型則能很好地滿足這種需求。很多應用都會從這種非結構化數據模型中獲益,比如說CRM、ERP、BPM等等,他們可以通過這種靈活性存儲數據而無需修改表或是創建更多的列。這些資料庫也非常適合於創建原型或是快速應用,因為這種靈活性使得新特性的開發變得非常容易。
如果有很多用戶在頻繁且並發地使用你的應用,那麼你就需要考慮可伸縮的資料庫技術而非傳統的RDBMS了。對於關係型技術來說,很多應用開發者會發現動態的可伸縮性是難以實現的,這時就應該考慮切換到NoSQL資料庫上。對於雲應用來說,關係型資料庫一開始是普遍的選擇。然而,在使用過程中卻遇到了越來越多的問題,原因就在於他們是中心化的,向上擴展而非水平擴展的。這使得他們不適合於那些需要簡單且動態可伸縮性的應用。NoSQL資料庫從一開始就是分布式、水平擴展的,因此非常適合於網際網路應用分布式的特性。
在三層網際網路架構的Web/應用層上,多年來向上擴展已經成為默認的擴展方式了。隨著應用使用人數的激增,我們需要添加更多的伺服器,性能則是通過負載均衡來實現的,這時的代價與用戶數量成線性比例關係。在NoSQL資料庫之前,資料庫層的默認擴展方式就是向上擴展。為了支持更多的並發用戶以及存儲更多的數據,你需要越來越好的伺服器,更好的CPU、更多的內存、更大的磁碟來維護所有表。然而,好的伺服器意味著更加複雜、私有、並且也更加昂貴。這與Web/應用層所使用的便宜的硬體形成了鮮明的對比。
3、動態模式
關係型資料庫需要在添加數據前先定義好模式。比如說,你需要存儲客戶的電話號碼、姓名、地址、城市與州等信息,SQL資料庫需要提前知曉你要存的是什麼。這對於敏捷開發模式來說是場災難,因為每次完成新特性時,資料庫的模式通常都需要改變。因此,如果在開發過程中想將客戶喜歡的條目加到資料庫中,那就得向表中添加這一列才行,然後要做的就是將整個資料庫遷移到新的模式上。
4、自動分片
由於是結構化的,關係型資料庫通常會垂直擴展,單台伺服器要持有整個資料庫來確保可靠性與數據的持續可用性。這樣做的代價就是非常昂貴、擴展受到限制,並且資料庫基礎設施會成為失敗點。這個問題的解決方案就是水平擴展,添加伺服器而不是為單台伺服器增加更多的能力。NoSQL資料庫通常都支持自動分片,這意味著他們本質上就會自動在多台伺服器上分發數據,應用甚至都不知道這些事情。數據與查詢負載會自動在多台伺服器上做到平衡,當某台伺服器當機時,它能快速且透明地被替換掉。
大多數NoSQL資料庫也支持自動複製,這意味著你可以獲得高可用性與災備恢復功能。從開發者的角度來看,存儲環境本質上是虛擬化的。
RDBMS系統由來已久。NoSQL擁護者們會說RDBMS的高齡是其衰退的標誌,不過對於大多數CIO來說,RDBMS的成熟讓人放心。對於大多數情況來說,RDBMS系統是穩定且功能豐富的。相比較而言,大多數NoSQL資料庫則還有很多特性有待實現。
企業需要的是安心,如果關鍵系統出現了故障,他們可以獲得即時的支持。所有RDBMS廠商都在不遺餘力地提供良好的企業支持。與之相反,大多數NoSQL系統都是開源項目,雖然每種資料庫都有那麼幾家公司提供支持,不過這些公司大多都是小的初創公司,沒有全球支持資源,也沒有Oracle、微軟或是IBM那種令人放心的公信力。
3、分析與商業智能
NoSQL資料庫在Web 2.0應用時代開始出現。因此,大多數特性都是面向這些應用的需要的。然而,應用中的數據對於業務來說是有價值的,這種價值遠遠超出了Web應用那種CRUD。企業資料庫中的業務信息可以幫助改進效率並提升競爭力,商業智能對於大中型企業來說是個非常關鍵的IT問題。
NoSQL的設計目標是提供零管理的解決方案,不過當今的現實卻離這個目標還相去甚遠。現在的NoSQL需要很多技巧才能用好,並且需要不少人力、物力來維護。
全球有很多開發者,每個業務部門都會有熟悉RDBMS概念與編程的人。相反,幾乎每個NoSQL開發者都處於學習模式。這種狀況會隨著時間的流逝而發生改觀。但現在,找到一個有經驗的RDBMS程式設計師或是管理員要比NoSQL專家容易多了。
NoSQL資料庫正在成為資料庫領域的重要力量。如果使用恰當,那麼它會帶來很多好處。然而,企業應該非常小心並注意到這些資料庫的限制與問題。
NoSQL這兩年越來越熱,尤其是大型網際網路公司非常熱衷這門技術。根據筆者的經驗,並不是任何場景,NoSQL都要優於關係型資料庫。下面我們來具體聊聊,什麼時候使用NoSQL比較給力:
1) 資料庫表schema經常變化
比如在線商城,維護產品的屬性經常要增加欄位,這就意味著ORMapping層的代碼和配置要改,如果該表的數據量過百萬,新增欄位會帶來額外開銷(重建索引等)。NoSQL應用在這種場景,可以極大提升DB的可伸縮性,開發人員可以將更多的精力放在業務層。
2)資料庫表欄位是複雜數據類型
對於複雜數據類型,比如SQL Sever提供了可擴展性的支持,像xml類型的欄位。很多用過的同學應該知道,該欄位不管是查詢還是更改,效率非常一般。主要原因是是DB層對xml欄位很難建高效索引,應用層又要做從字符流到dom的解析轉換。NoSQL以json方式存儲,提供了原生態的支持,在效率方便遠遠高於傳統關係型資料庫。
3)高並發資料庫請求
此類應用常見於web2.0的網站,很多應用對於數據一致性要求很低,而關係型資料庫的事務以及大表join反而成了」性能殺手」。在高並發情況下,sql與no-sql的性能對比由於環境和角度不同一直是存在爭議的,並不是說在任何場景,no-sql總是會比sql快。
4)海量數據的分布式存儲
海量數據的存儲如果選用大型商用數據,如Oracle,那麼整個解決方案的成本是非常高的,要花很多錢在軟硬體上。NoSQL分布式存儲,可以部署在廉價的硬體上,是一個性價比非常高的解決方案。Mongo的auto-sharding已經運用到了生產環境。
並不是說NoSQL可以解決一切問題,像ERP系統、BI系統,在大部分情況還是推薦使用傳統關係型資料庫。主要的原因是此類系統的業務模型複雜,使用NoSQL將導致系統的維護成本增加。
為什麼要使用NoSQL
NoSQL概念
隨著web2.0的快速發展,非關係型、分布式數據存儲得到了快速的發展,它們不保證關係數據的ACID特性。NoSQL概念在2009年被提了出來。NoSQL最常見的解釋是「non-relational」,「Not Only SQL」也被很多人接受。(「NoSQL」一詞最早於1998年被用於一個輕量級的關係資料庫的名字。)
NoSQL被我們用得最多的當數key-value存儲,當然還有其他的文檔型的、列存儲、圖型資料庫、xml資料庫等。在NoSQL概念提出之前,這些資料庫就被用於各種系統當中,但是卻很少用於web網際網路應用。比如cdb、qdbm、bdb資料庫。
傳統關係資料庫的瓶頸
傳統的關係資料庫具有不錯的性能,高穩定型,久經歷史考驗,而且使用簡單,功能強大,同時也積累了大量的成功案例。在網際網路領域,MySQL成為了絕對靠前的王者,毫不誇張的說,MySQL為網際網路的發展做出了卓越的貢獻。
在90年代,一個網站的訪問量一般都不大,用單個資料庫完全可以輕鬆應付。在那個時候,更多的都是靜態網頁,動態交互類型的網站不多。
到了最近10年,網站開始快速發展。火爆的論壇、博客、sns、微博逐漸引領web領域的潮流。在初期,論壇的流量其實也不大,如果你接觸網絡比較早,你可能還記得那個時候還有文本型存儲的論壇程序,可以想像一般的論壇的流量有多大。
Memcached+MySQL
後來,隨著訪問量的上升,幾乎大部分使用MySQL架構的網站在資料庫上都開始出現了性能問題,web程序不再僅僅專注在功能上,同時也在追求性能。程式設計師們開始大量的使用緩存技術來緩解資料庫的壓力,優化資料庫的結構和索引。開始比較流行的是通過文件緩存來緩解資料庫壓力,但是當訪問量繼續增大的時候,多台web機器通過文件緩存不能共享,大量的小文件緩存也帶了了比較高的IO壓力。在這個時候,Memcached就自然的成為一個非常時尚的技術產品。
Memcached作為一個獨立的分布式的緩存伺服器,為多個web伺服器提供了一個共享的高性能緩存服務,在Memcached伺服器上,又發展了根據hash算法來進行多台Memcached緩存服務的擴展,然後又出現了一致性hash來解決增加或減少緩存伺服器導致重新hash帶來的大量緩存失效的弊端。
Mysql主從讀寫分離
由於資料庫的寫入壓力增加,Memcached只能緩解資料庫的讀取壓力。讀寫集中在一個資料庫上讓資料庫不堪重負,大部分網站開始使用主從複製技術來達到讀寫分離,以提高讀寫性能和讀庫的可擴展性。Mysql的master-slave模式成為這個時候的網站標配了。
分表分庫
隨著web2.0的繼續高速發展,在Memcached的高速緩存,MySQL的主從複製,讀寫分離的基礎之上,這時MySQL主庫的寫壓力開始出現瓶頸,而數據量的持續猛增,由於MyISAM使用表鎖,在高並發下會出現嚴重的鎖問題,大量的高並發MySQL應用開始使用InnoDB引擎代替MyISAM。同時,開始流行使用分表分庫來緩解寫壓力和數據增長的擴展問題。這個時候,分表分庫成了一個熱門技術,是面試的熱門問題也是業界討論的熱門技術問題。也就在這個時候,MySQL推出了還不太穩定的表分區,這也給技術實力一般的公司帶來了希望。雖然MySQL推出了MySQL Cluster集群,但是由於在網際網路幾乎沒有成功案例,性能也不能滿足網際網路的要求,只是在高可靠性上提供了非常大的保證。
MySQL的擴展性瓶頸
在網際網路,大部分的MySQL都應該是IO密集型的,事實上,如果你的MySQL是個CPU密集型的話,那麼很可能你的MySQL設計得有性能問題,需要優化了。大數據量高並發環境下的MySQL應用開發越來越複雜,也越來越具有技術挑戰性。分表分庫的規則把握都是需要經驗的。雖然有像淘寶這樣技術實力強大的公司開發了透明的中間件層來屏蔽開發者的複雜性,但是避免不了整個架構的複雜性。分庫分表的子庫到一定階段又面臨擴展問題。還有就是需求的變更,可能又需要一種新的分庫方式。
MySQL資料庫也經常存儲一些大文本欄位,導致資料庫表非常的大,在做資料庫恢復的時候就導致非常的慢,不容易快速恢複數據庫。比如1000萬4KB大小的文本就接近40GB的大小,如果能把這些數據從MySQL省去,MySQL將變得非常的小。
關係資料庫很強大,但是它並不能很好的應付所有的應用場景。MySQL的擴展性差(需要複雜的技術來實現),大數據下IO壓力大,表結構更改困難,正是當前使用MySQL的開發人員面臨的問題。
NOSQL的優勢
易擴展
NoSQL資料庫種類繁多,但是一個共同的特點都是去掉關係資料庫的關係型特性。數據之間無關係,這樣就非常容易擴展。也無形之間,在架構的層面上帶來了可擴展的能力。
大數據量,高性能
NoSQL資料庫都具有非常高的讀寫性能,尤其在大數據量下,同樣表現優秀。這得益於它的無關係性,資料庫的結構簡單。一般MySQL使用Query Cache,每次表的更新Cache就失效,是一種大粒度的Cache,在針對web2.0的交互頻繁的應用,Cache性能不高。而NoSQL的Cache是記錄級的,是一種細粒度的Cache,所以NoSQL在這個層面上來說就要性能高很多了。
靈活的數據模型
NoSQL無需事先為要存儲的數據建立欄位,隨時可以存儲自定義的數據格式。而在關係資料庫里,增刪欄位是一件非常麻煩的事情。如果是非常大數據量的表,增加欄位簡直就是一個噩夢。這點在大數據量的web2.0時代尤其明顯。
高可用
NoSQL在不太影響性能的情況,就可以方便的實現高可用的架構。比如Cassandra,HBase模型,通過複製模型也能實現高可用。
總結
NoSQL資料庫的出現,彌補了關係數據(比如MySQL)在某些方面的不足,在某些方面能極大的節省開發成本和維護成本。
MySQL和NoSQL都有各自的特點和使用的應用場景,兩者的緊密結合將會給web2.0的資料庫發展帶來新的思路。讓關係資料庫關注在關係上,NoSQL關注在存儲上。
關係資料庫還是NoSQL資料庫
在過去,我們只需要學習和使用一種資料庫技術,就能做幾乎所有的資料庫應用開發。因為成熟穩定的關係資料庫產品並不是很多,而供你選擇的免費版本就更加少了,所以網際網路領域基本上都選擇了免費的MySQL資料庫。在高速發展的WEB2.0時代,我們發現關係資料庫在性能、擴展性、數據的快速備份和恢復、滿足需求的易用性上並不總是能很好的滿足我們的需要,我們越來越趨向於根據業務場景選擇合適的資料庫,以及進行多種資料庫的融合運用。
當我們在討論是否要使用NoSQL的時候,你還需要理解NoSQL也是分很多種類的,在NoSQL百花齊放的今天,NoSQL的正確選擇比選擇關係資料庫還具有挑戰性。雖然NoSQL的使用很簡單,但是選擇卻是個麻煩事,這也正是很多人在觀望的一個原因。
NoSQL的分類
NoSQL僅僅是一個概念,NoSQL資料庫根據數據的存儲模型和特點分為很多種類。
以上NoSQL資料庫類型的劃分並不是絕對,只是從存儲模型上來進行的大體劃分。它們之間沒有絕對的分界,也有交差的情況,比如Tokyo Cabinet / Tyrant的Table類型存儲,就可以理解為是文檔型存儲,Berkeley DB XML資料庫是基於Berkeley DB之上開發的。
NoSQL還是關係資料庫
雖然09年出現了比較激進的文章《關係資料庫已死》,但是我們心裡都清楚,關係資料庫其實還活得好好的,你還不能不用關係資料庫。但是也說明了一個事實,關係資料庫在處理WEB2.0數據的時候,的確已經出現了瓶頸。
那麼我們到底是用NoSQL還是關係資料庫呢?我想我們沒有必要來進行一個絕對的回答。我們需要根據我們的應用場景來決定我們到底用什麼。
如果關係資料庫在你的應用場景中,完全能夠很好的工作,而你又是非常善於使用和維護關係資料庫的,那麼我覺得你完全沒有必要遷移到NoSQL上面,除非你是個喜歡折騰的人。如果你是在金融,電信等以數據為王的關鍵領域,目前使用的是Oracle資料庫來提供高可靠性的,除非遇到特別大的瓶頸,不然也別貿然嘗試NoSQL。
然而,在WEB2.0的網站中,關係資料庫大部分都出現了瓶頸。在磁碟IO、資料庫可擴展上都花費了開發人員相當多的精力來優化,比如做分表分庫(database sharding)、主從複製、異構複製等等,然而,這些工作需要的技術能力越來越高,也越來越具有挑戰性。如果你正在經歷這些場合,那麼我覺得你應該嘗試一下NoSQL了。
選擇合適的NoSQL
如此多類型的NoSQL,而每種類型的NoSQL又有很多,到底選擇什麼類型的NoSQL來作為我們的存儲呢?這並不是一個很好回答的問題,影響我們選擇的因素有很多,而選擇也可能有多種,隨著業務場景,需求的變更可能選擇又會變化。我們常常需要根據如下情況考慮:
1、數據結構特點。包括結構化、半結構化、欄位是否可能變更、是否有大文本欄位、數據欄位是否可能變化。
2、寫入特點。包括insert比例、update比例、是否經常更新數據的某一個小欄位、原子更新需求。
3、查詢特點。包括查詢的條件、查詢熱點的範圍。比如用戶信息的查詢,可能就是隨機的,而新聞的查詢就是按照時間,越新的越頻繁。
NoSQL和關係資料庫結合
其實NoSQL資料庫僅僅是關係資料庫在某些方面(性能,擴展)的一個彌補,單從功能上講,NoSQL的幾乎所有的功能,在關係資料庫上都能夠滿足,所以選擇NoSQL的原因並不在功能上。
所以,我們一般會把NoSQL和關係資料庫進行結合使用,各取所長,需要使用關係特性的時候我們使用關係資料庫,需要使用NoSQL特性的時候我們使用NoSQL資料庫,各得其所。
舉個簡單的例子吧,比如用戶評論的存儲,評論大概有主鍵id、評論的對象aid、評論內容content、用戶uid等欄位。我們能確定的是評論內容content肯定不會在資料庫中用where content=』』查詢,評論內容也是一個大文本欄位。那麼我們可以把 主鍵id、評論對象aid、用戶id存儲在資料庫,評論內容存儲在NoSQL,這樣資料庫就節省了存儲content占用的磁碟空間,從而節省大量IO,對content也更容易做Cache。
在某些應用場合,比如一些配置的關係鍵值映射存儲、用戶名和密碼的存儲、Session會話存儲等等,用NoSQL完全可以替代MySQL存儲。不但具有更高的性能,而且開發也更加方便。
NoSQL作為緩存伺服器
MySQL+Memcached的架構中,我們處處都要精心設計我們的緩存,包括過期時間的設計、緩存的實時性設計、緩存內存大小評估、緩存命中率等等。
NoSQL資料庫一般都具有非常高的性能,在大多數場景下面,你不必再考慮在代碼層為NoSQL構建一層Memcached緩存。NoSQL數據本身在Cache上已經做了相當多的優化工作。
Memcached這類內存緩存伺服器緩存的數據大小受限於內存大小,如果用NoSQL來代替Memcached來緩存資料庫的話,就可以不再受限於內存大小。雖然可能有少量的磁碟IO讀寫,可能比Memcached慢一點,但是完全可以用來緩存資料庫的查詢操作。
規避風險
現在業內很多公司的做法就是數據的備份。在往NoSQL裡面存儲數據的時候還會往MySQL裡面存儲一份。NoSQL資料庫本身也需要進行備份(冷備和熱備)。或者可以考慮使用兩種NoSQL資料庫,出現問題後可以進行切換(避免出現digg使用Cassandra的悲劇)。
總結
本文只是簡單的從MySQL和NoSQL的角度分析如何選擇,以及進行融合使用。其實在選擇NoSQL的時候,你可能還會碰到關於CAP原則,最終一致性,BASE思想的考慮。因為使用MySQL架構的時候,你也會碰到上面的問題,所以這裡沒有闡述。

留言

這個網誌中的熱門文章

Json概述以及python對json的相關操作

Docker容器日誌查看與清理

利用 Keepalived 提供 VIP