隨著大數(shù)據(jù)時代的到來,越來越多的網(wǎng)站、應(yīng)用系統(tǒng)需要支撐海量數(shù)據(jù)存儲,高并發(fā)請求、高可用、高可擴(kuò)展性等特性要求,傳統(tǒng)的關(guān)系型數(shù)據(jù)庫在應(yīng)付這些調(diào)整已經(jīng)顯得力不從心,暴露了許多能以克服的問題。由此,各種各樣的NoSQL(Not Only SQL)數(shù)據(jù)庫作為傳統(tǒng)關(guān)系型數(shù)據(jù)的一個有力補(bǔ)充得到迅猛發(fā)展。 本文將分析傳統(tǒng)數(shù)據(jù)庫的存在的相關(guān)問題,以及幾大類NoSQL如何解決這些問題,希望給大家提供在不同業(yè)務(wù)場景下,關(guān)于存儲方面技術(shù)選型提供參考。 1 傳統(tǒng)數(shù)據(jù)庫缺點
2 NoSQL解決方案NoSQL,泛指非關(guān)系型的數(shù)據(jù)庫,可以理解為SQL的一個有力補(bǔ)充。 在NoSQL許多方面性能大大優(yōu)于非關(guān)系型數(shù)據(jù)庫的同時,往往也伴隨一些特性的缺失,比較常見的,是事務(wù)庫事務(wù)功能的缺失。 數(shù)據(jù)庫事務(wù)正確執(zhí)行的四個基本要素:ACID如下: 名稱 描述 A Atomicity (原子性) 一個事務(wù)中的所有操作,要么全部完成,要么全部不完成,不會在中間某個環(huán)節(jié)結(jié)束。 事務(wù)在執(zhí)行過程中發(fā)生錯誤,會被回滾到事務(wù)開始前的狀態(tài),就像這個事務(wù)從來沒有執(zhí)行過一樣。 C Consistency 一致性 在事務(wù)開始之前和事務(wù)結(jié)束以后,數(shù)據(jù)庫的完整性沒有被破壞。 I Isolation 隔離性 數(shù)據(jù)庫允許多個并發(fā)事務(wù)同時對數(shù)據(jù)進(jìn)行讀寫和修改的能力。隔離性可以防止多個事務(wù)并發(fā)執(zhí)行時由于交叉執(zhí)行而導(dǎo)致數(shù)據(jù)的不一致。 D Durability 持久性 事務(wù)處理結(jié)束后,對數(shù)據(jù)的修改就是永久的,即便系統(tǒng)故障也不會丟失。 下面介紹5大類NoSQL數(shù)據(jù)針對傳統(tǒng)關(guān)系型數(shù)據(jù)庫的缺點提供的解決方案: 2.1 列式數(shù)據(jù)庫 列式數(shù)據(jù)庫是以列相關(guān)存儲架構(gòu)進(jìn)行數(shù)據(jù)存儲的數(shù)據(jù)庫,主要適合于批量數(shù)據(jù)處理和即時查詢。相對應(yīng)的是行式數(shù)據(jù)庫,數(shù)據(jù)以行相關(guān)的存儲體系架構(gòu)進(jìn)行空間分配,主要適合于小批量的數(shù)據(jù)處理,常用于聯(lián)機(jī)事務(wù)型數(shù)據(jù)處理。 基于列式數(shù)據(jù)庫的列列存儲特性,可以解決某些特定場景下關(guān)系型數(shù)據(jù)庫I/O較高的問題 2.1.1 基本原理 傳統(tǒng)關(guān)系型數(shù)據(jù)庫是按照行來存儲數(shù)據(jù)庫,稱為“行式數(shù)據(jù)庫”,而列式數(shù)據(jù)庫是按照列來存儲數(shù)據(jù)。 將表放入存儲系統(tǒng)中有兩種方法,而我們絕大部分是采用行存儲的。 行存儲法是將各行放入連續(xù)的物理位置,這很像傳統(tǒng)的記錄和文件系統(tǒng)。 列存儲法是將數(shù)據(jù)按照列存儲到數(shù)據(jù)庫中,與行存儲類似,下圖是兩種存儲方法的圖形化解釋: 2.1.2 常見列式數(shù)據(jù)庫
HBase是一個開源的非關(guān)系型分布式數(shù)據(jù)庫(NoSQL),它參考了谷歌的BigTable建模,實現(xiàn)的編程語言為 Java。它是Apache軟件基金會的Hadoop項目的一部分,運行于HDFS文件系統(tǒng)之上,為 Hadoop 提供類似于BigTable 規(guī)模的服務(wù)。因此,它可以容錯地存儲海量稀疏的數(shù)據(jù)。
BigTable是一種壓縮的、高性能的、高可擴(kuò)展性的,基于Google文件系統(tǒng)(Google File System,GFS)的數(shù)據(jù)存儲系統(tǒng),用于存儲大規(guī)模結(jié)構(gòu)化數(shù)據(jù),適用于云端計算。 2.1.3 相關(guān)特性 優(yōu)點如下:
列式數(shù)據(jù)庫由于其針對不同列的數(shù)據(jù)特征而發(fā)明的不同算法使其往往有比行式數(shù)據(jù)庫高的多的壓縮率,普通的行式數(shù)據(jù)庫一般壓縮率在3:1 到5:1 左右,而列式數(shù)據(jù)庫的壓縮率一般在8:1到30:1 左右。 比較常見的,通過字典表壓縮數(shù)據(jù): 下面中才是那張表本來的樣子。經(jīng)過字典表進(jìn)行數(shù)據(jù)壓縮后,表中的字符串才都變成數(shù)字了。正因為每個字符串在字典表里只出現(xiàn)一次了,所以達(dá)到了壓縮的目的(有點像規(guī)范化和非規(guī)范化Normalize和Denomalize)
讀取多條數(shù)據(jù)的同一列效率高,因為這些列都是存儲在一起的,一次磁盤操作可以數(shù)據(jù)的指定列全部讀取到內(nèi)存中。 下圖通過一條查詢的執(zhí)行過程說明列式存儲(以及數(shù)據(jù)壓縮)的優(yōu)點 執(zhí)行步驟如下: i. 去字典表里找到字符串對應(yīng)數(shù)字(只進(jìn)行一次字符串比較)。 ii. 用數(shù)字去列表里匹配,匹配上的位置設(shè)為1。 iii. 把不同列的匹配結(jié)果進(jìn)行位運算得到符合所有條件的記錄下標(biāo)。 iv. 使用這個下標(biāo)組裝出最終的結(jié)果集。 復(fù)制代碼
缺點如下:
2.1.4 使用場景 以HBase為例說明:
2.2 K-V數(shù)據(jù)庫指的是使用鍵值(key-value)存儲的數(shù)據(jù)庫,其數(shù)據(jù)按照鍵值對的形式進(jìn)行組織、索引和存儲。 KV 存儲非常適合不涉及過多數(shù)據(jù)關(guān)系業(yè)務(wù)關(guān)系的數(shù)據(jù),同時能有效減少讀寫磁盤的次數(shù),比 SQL 數(shù)據(jù)庫存儲擁有更好的讀寫性能,能夠解決關(guān)系型數(shù)據(jù)庫無法存儲數(shù)據(jù)結(jié)構(gòu)的問題。 2.2.1 常見 K-V數(shù)據(jù)庫
Redis是一個使用ANSI C編寫的開源、支持網(wǎng)絡(luò)、基于內(nèi)存、可選持久性的鍵值對存儲數(shù)據(jù)庫。從2015年6月開始,Redis的開發(fā)由Redis Labs贊助,而2013年5月至2015年6月期間,其開發(fā)由Pivotal贊助。在2013年5月之前,其開發(fā)由VMware贊助。根據(jù)月度排行網(wǎng)站DB-Engines.com的數(shù)據(jù)顯示,Redis是最流行的鍵值對存儲數(shù)據(jù)庫。
Apache Cassandra(社區(qū)內(nèi)一般簡稱為C*)是一套開源分布式NoSQL數(shù)據(jù)庫系統(tǒng)。它最初由Facebook開發(fā),用于儲存收件箱等簡單格式數(shù)據(jù),集Google BigTable的數(shù)據(jù)模型與Amazon Dynamo的完全分布式架構(gòu)于一身。Facebook于2008將 Cassandra 開源,此后,由于Cassandra良好的可擴(kuò)展性和性能,被 Apple, Comcast,Instagram, Spotify, eBay, Rackspace, Netflix等知名網(wǎng)站所采用,成為了一種流行的分布式結(jié)構(gòu)化數(shù)據(jù)存儲方案。
2.2.2 相關(guān)特性 以Redis為例: 優(yōu)點如下:
缺點如下: 針對ACID,Redis事務(wù)不能支持原子性和持久性(A和D),只支持隔離性和一致性(I和C) 特別說明一下,這里所說的無法保證原子性,是針對Redis的事務(wù)操作,因為事務(wù)是不支持回滾(roll back),而因為Redis的單線程模型,Redis的普通操作是原子性的 大部分業(yè)務(wù)不需要嚴(yán)格遵循ACID原則,例如游戲?qū)崟r排行榜,粉絲關(guān)注等場景,即使部分?jǐn)?shù)據(jù)持久化失敗,其實業(yè)務(wù)影響也非常小。因此在設(shè)計方案時,需要根據(jù)業(yè)務(wù)特征和要求來做選擇 2.2.3 使用場景
2.3 文檔數(shù)據(jù)庫 文檔數(shù)據(jù)庫(也稱為文檔型數(shù)據(jù)庫)是旨在將半結(jié)構(gòu)化數(shù)據(jù)存儲為文檔的一種數(shù)據(jù)庫。文檔數(shù)據(jù)庫通常以 JSON 或 XML 格式存儲數(shù)據(jù)。 由于文檔數(shù)據(jù)庫的no-schema特性,可以存儲和讀取任意數(shù)據(jù)。 由于使用的數(shù)據(jù)格式是JSON或者BSON,因為JSON數(shù)據(jù)是自描述的,無需在使用前定義字段,讀取一個JSON中不存在的字段也不會導(dǎo)致SQL那樣的語法錯誤,可以解決關(guān)系型數(shù)據(jù)庫表結(jié)構(gòu)schema擴(kuò)展不方便的問題 2.3.1 常見文檔數(shù)據(jù)庫
MongoDB是一種面向文檔的數(shù)據(jù)庫管理系統(tǒng),由C++撰寫而成,以此來解決應(yīng)用程序開發(fā)社區(qū)中的大量現(xiàn)實問題。2007年10月,MongoDB由10gen團(tuán)隊所發(fā)展。2009年2月首度推出。
Apache CouchDB是一個開源數(shù)據(jù)庫,專注于易用性和成為'完全擁抱web的數(shù)據(jù)庫'。它是一個使用JSON作為存儲格式,JavaScript作為查詢語言,MapReduce和HTTP作為API的NoSQL數(shù)據(jù)庫。其中一個顯著的功能就是多主復(fù)制。CouchDB的第一個版本發(fā)布在2005年,在2008年成為了Apache的項目。 2.3.2 相關(guān)特性 以MongoDB為例進(jìn)行說明 優(yōu)點如下:
相比傳統(tǒng)關(guān)系型數(shù)據(jù)庫,文檔數(shù)據(jù)庫的缺點主要是對多條數(shù)據(jù)記錄的事務(wù)支持較弱,具體體現(xiàn)如下:
MongonDB還是支持多文檔事務(wù)的Consistency(一致性)和Durability(持久性) 雖然官方宣布MongoDB將在4.0版本中正式推出多文檔ACID事務(wù)支持,最后落地情況還有待見證。 2.3.3 使用場景 適用場景:
不適用場景:
2.4 全文搜索引擎 傳統(tǒng)關(guān)系型數(shù)據(jù)庫主要通過索引來達(dá)到快速查詢的目的,在全文搜索的業(yè)務(wù)下,索引也無能為力,主要體現(xiàn)在:
而全文搜索引擎的出現(xiàn),正是解決關(guān)系型數(shù)據(jù)庫全文搜索功能較弱的問題 2.4.1 基本原理 全文搜索引擎的技術(shù)原理稱為“倒排索引”(inverted index),是一種索引方法,其基本原理是建立單詞到文檔的索引。與之相對是,是“正排索引”,其基本原理是建立文檔到單詞的索引。 現(xiàn)在有如下文檔集合: 正排索引得到索引如下: 可見,正排索引適用于根據(jù)文檔名稱查詢文檔內(nèi)容 簡單的倒排索引如下: 帶有單詞頻率信息的倒排索引如下: 可見,倒排索引適用于根據(jù)關(guān)鍵詞來查詢文檔內(nèi)容 2.4.2 常見全文搜索引擎
2.4.3 相關(guān)特性 以Elasticsearch為例: 優(yōu)點如下:
缺點如下:
2.4.4 使用場景 適用場景如下:
不適用場景如下:
2.5 圖形數(shù)據(jù)庫 圖形數(shù)據(jù)庫應(yīng)用圖形理論存儲實體之間的關(guān)系信息。最常見例子就是社會網(wǎng)絡(luò)中人與人之間的關(guān)系。關(guān)系型數(shù)據(jù)庫用于存儲“關(guān)系型”數(shù)據(jù)的效果并不好,其查詢復(fù)雜、緩慢、超出預(yù)期,而圖形數(shù)據(jù)庫的獨特設(shè)計恰恰彌補(bǔ)了這個缺陷,解決關(guān)系型數(shù)據(jù)庫存儲和處理復(fù)雜關(guān)系型數(shù)據(jù)功能較弱的問題。 2.5.1 常見圖形數(shù)據(jù)庫
Neo4j是由Neo4j,Inc。開發(fā)的圖形數(shù)據(jù)庫管理系統(tǒng)。由其開發(fā)人員描述為具有原生圖存儲和處理的符合ACID的事務(wù)數(shù)據(jù)庫,根據(jù)DB-Engines排名, Neo4j是最流行的圖形數(shù)據(jù)庫。
ArangoDB是由triAGENS GmbH開發(fā)的原生多模型數(shù)據(jù)庫系統(tǒng)。數(shù)據(jù)庫系統(tǒng)支持三個重要的數(shù)據(jù)模型(鍵/值,文檔,圖形),其中包含一個數(shù)據(jù)庫核心和統(tǒng)一查詢語言AQL(ArangoDB查詢語言)。查詢語言是聲明性的,允許在單個查詢中組合不同的數(shù)據(jù)訪問模式。ArangoDB是一個NoSQL數(shù)據(jù)庫系統(tǒng),但AQL在很多方面與SQL類似。
Titan是一個可擴(kuò)展的圖形數(shù)據(jù)庫,針對存儲和查詢包含分布在多機(jī)群集中的數(shù)百億個頂點和邊緣的圖形進(jìn)行了優(yōu)化。Titan是一個事務(wù)性數(shù)據(jù)庫,可以支持?jǐn)?shù)千個并發(fā)用戶實時執(zhí)行復(fù)雜的圖形遍歷。 2.5.2 相關(guān)特性 以Neo4j為例: Neo4j 使用數(shù)據(jù)結(jié)構(gòu)中圖(graph)的概念來進(jìn)行建模。 Neo4j 中兩個最基本的概念是節(jié)點和邊。節(jié)點表示實體,邊則表示實體之間的關(guān)系。節(jié)點和邊都可以有自己的屬性。不同實體通過各種不同的關(guān)系關(guān)聯(lián)起來,形成復(fù)雜的對象圖。 針對關(guān)系數(shù)據(jù),2種2數(shù)據(jù)庫的存儲結(jié)構(gòu)不同: Neo4j中,存儲節(jié)點時使用了”index-free adjacency”,即每個節(jié)點都有指向其鄰居節(jié)點的指針,可以讓我們在O(1)的時間內(nèi)找到鄰居節(jié)點。另外,按照官方的說法,在Neo4j中邊是最重要的,是”first-class entities”,所以單獨存儲,這有利于在圖遍歷的時候提高速度,也可以很方便地以任何方向進(jìn)行遍歷 如下優(yōu)點:
缺點如下:
2.5.3 使用場景 適用場景如下:
不適用場景如下:
3 總結(jié)關(guān)系型數(shù)據(jù)庫和NoSQL數(shù)據(jù)庫的選型,往往需要考慮幾個指標(biāo):
常見軟件系統(tǒng)數(shù)據(jù)庫選型參考如下:
設(shè)計實踐中,要基于需求、業(yè)務(wù)驅(qū)動架構(gòu),無論選用RDB/NoSQL/DRDB,一定是以需求為導(dǎo)向,最終數(shù)據(jù)存儲方案必然是各種權(quán)衡的綜合性設(shè)計 |
|
來自: 馬武彬 > 《技術(shù)文檔材料》