第四篇:SQL

穆晨發表於2016-03-17

前言

        確實,關於SQL的學習資料,各類文件在網上到處都是。但它們絕大多數的出發點都侷限在舊有關聯式資料庫裡,內容近乎千篇一律。而在當今大資料的浪潮下,SQL早就被賦予了新的責任和意義。

        本篇中,筆者將結合過去在A公司和T公司大資料部門的學習工作經歷,對傳統SQL語法進行一次回顧性學習。同時,思考這門語言在大資料時代的重要意義。

大資料技術中SQL的作用

        SQL的全稱為Structured Query Language,也即結構化查詢語言。關聯式資料庫中,SQL是使用者使用資料庫的基本手段,它能用於建立資料庫或者關係,能對資料庫中各關係進行增刪改查,還能對資料庫進行維護和管理等等。而隨著分散式計算平臺如Hadoop,Spark的興起,SQL的應用範圍發生了較大變化,但它作為資料分析核心的地位,始終沒有動搖。在新的背景下,SQL語言具有以下新的意義:

        1. 管理大型分散式資料倉儲系統中的"元倉"

        所謂"元倉",可以理解為存放後設資料的資料庫。關聯式資料庫中叫資料字典(data dictionary),而Hadoop平臺的資料倉儲工具Hive或Spark平臺的Spark SQL則將其稱為metastore。在這類分散式的倉儲系統裡,資料計算都是在分散式平臺上進行,但其metastore幾乎都是建立在傳統的關聯式資料庫(如MySQL)上。

        那麼後設資料又是什麼?對大資料計算分析平臺重要嗎?

        舉個例子,筆者之前所在的A公司其雲端計算系統可以說是國內業界最強。在該公司的某個巨型大資料離線計算平臺的元倉裡,主要存放的後設資料有各關係的基本資訊(表名列名等),資料血緣及排程依賴關係,資料許可權關係,資料資產關係  ,資料監控關係等等,如下圖所示:

        而基於元倉,還可以開發出類似資料地圖系統,資料資產管理系統,資料質量工程系統等高階資料管理工具供公司各類開發人員使用。關於這些資料在分散式平臺的採集、管理屬於一個非常有趣而有挑戰的話題,甚至可能是將來雲端計算髮展的一個重要趨勢所在。但由於這部分比較多的涉及到商業機密,本文點到為止了。

        回到主題,讀者想必對元倉的重要性有了感悟。而元倉又是存放在關聯式資料庫裡,因此要想管理好元倉,你需要熟練掌握SQL

        2. 操作大資料平臺完成資料分析任務

        瞭解大資料技術的童鞋想必清楚,Hadoop平臺沒有實現資料庫,其核心只在於MapReduce程式設計框架和Hdfs檔案系統。但如果每個計算任務都要寫MR程式碼,那是很讓人抓狂的。這點很快就被Apache公司注意到,並針對該問題釋出了Hive資料倉儲工具。這個工具提供一種類SQL的語言,使用者能直接使用它進行資料分析,而它則負責將類SQL語言轉化為MR程式碼,提交Hadoop平臺執行。Hive在Hadoop生態圈中的意義恐怕不是最大也是最大之一,很多公司甚至就單純為了使用Hive而搭建的Hadoop環境。所以為了不糾結於分散式程式碼縮減開發成本,你需要熟練掌握SQL

        3. 線上報表展示

        再舉個例子,筆者在T公司工作時,在利用大資料分析平臺進行資料分析後,最終結果需要提交到線上報表系統以進行視覺化展示。但由於資料分析結果的量並不大,同時為了利用關聯式資料庫強一致性等優勢,資料分析的結果都要先從大資料平臺轉入關聯式資料庫,然後讓報表系統從關聯式資料庫中取數。所以為了順利高效的線上釋出資料分析結果,你需要熟練掌握SQL

        4. 其他

        以上部分僅僅是SQL應用的冰山一角。對於從事資料研發的人來說,無論在什麼環境框架下,都可能用到這門語言。以致於有些同事將之戲稱為"西闊心經":)。

SQL命令綜述

        SQL雖然基礎重要應用廣泛,但學起來卻比較容易。記得以前某人跟我說的,想成為一個特級廚師,基本刀功肯定不能差。那麼在接下來學習資料倉儲,資料探勘,深度學習等"高大上"技術之前,還是先好好鞏固一下"西闊心經"吧。

        總的來說,SQL語法可以劃分為幾大塊:


        1. 資料定義語言DDL:用於具體實現關係,以及關係附帶的一些結構,如索引等;

        2. 資料查詢語言DML:用於運算元據庫,包括增刪改查;

        3. 資料控制語言DCL:用來幫助實現資料庫的存取控制;

        4. 事務控制語言TCL:用於資料庫中的事務管理;

        接下來本文將對幾大類的SQL進行講解,採用回顧總結型的講解方式,不會涉及過多細節。

DDL

        資料定義語言DDL(Data Definition Language)的組成部分並不多,主要涉及到的關鍵字有:CREATE, ALTER, DROP這三個。

        1. CREATE

        用於建立資料庫,建立關係表,建立檢視等。需要注意的是在建表的時候除了表本身,還要定義主外來鍵約束,以及一些附帶結構,如索引等。

        2. ALTER

        用於調整資料庫/表/檢視的結構資訊。

        3. DROP

        用於刪除資料庫/表/檢視。要注意刪除的時候必須先刪除外碼所在關係,然後再刪除被外碼參照的主碼的關係。

DML

        資料查詢語言DML(Data Manipulation Language)是SQL的主體成分,SQL的編寫工作絕大部分都是在這一塊。該部分知識比較雜而多,故本文選擇從整體角度,以經驗總結的形式進行講解,相關語法細節請讀者查詢有關函式手冊。

        總的來說,DML有以下功能(底層項為功能所涉及關鍵字):

        1. 基本檢索

        SELECT+WHERE+GROUP BY(聚集函式)+HAVING+ORDER BY是最常用的查詢組合,要注意的是如果SELECT搭配了GROUP BY,那麼GROUP BY後列也要是SELECT的一部分,這樣查詢結果才能清楚展示資料是按什麼分組的。另一方面,如果使用了GROUP BY,那麼出現在SELECT後不使用聚集函式的列必須也出現在GROUP BY裡否則系統提示異常。新手常會犯這個錯誤,如以下程式碼:

SELECT id, name, count(*)
GROUP BY id

        name列沒有使用聚集函式,且沒有出現在GROUP BY後,因此係統必然提示出錯。

        因此請意識到GROUP BY後面跟了什麼列,SELECT後面就單寫什麼列(不使用聚合函式),出現的其他列則必須使用聚合函式。

        此外,HAVING後面跟著的約束物件必須是聚合函式列。雖然感覺是有點重複(聚合函式列寫了兩次),而且WHERE子句和HAVING子句中都不允許使用列別名...但若不滿足這些約束,查詢結果會混亂。

        2. 高階檢索

                a) 巢狀查詢:巢狀查詢的層數儘量不要太高,否則會影響查詢效率;

                b) 連線查詢:注意區分幾種JOIN的不同含義;

                c) 集合運算:集合運算的本質在於合併多條能"相融"的SQL語句;
        3. 插入語句

        插入語句的標準形式是INSERT INTO 表名 VALUES(表內容),沒有外碼的關係要優先執行插入。

        4. 更新語句

        更新語句的標準形式是UPDATE 表名 SET 列值='XX' WHERE 條件。

        5. 刪除語句

        刪除語句的標準形式DELETE FROM 表名 WHERE 條件。注意不要和刪除表的命令DROP搞混。

        6. 其他關鍵字

        沒啥好說的。

DCL & TCL

        資料控制語言DCL(Data Control Language)主要是管理資料庫許可權,負責資料的安全。最常用的是GRANT和ROVOKE命令。

        事務控制語言TCL(Transaction Control Language)則主要面向資料庫的備份和恢復兩大主題,常用命令為COMMIT和ROLLBACK。

小結

        SQL的學習並不難,但是如果要在具體環境下寫出高質量的SQL,則未必是一件容易的事情。不論是對於傳統的關係型資料庫,還是分散式倉儲系統如Hive、Spark SQL,SQL的優化都可以再單獨寫一本書了。最好在明確了要長期使用的資料分析平臺後,再深入針對性地學習專有SQL。比如選定了用Hive,那麼就要狠下功夫研究怎麼寫SQL才能避免"資料傾斜"問題。

        最後,一個優秀的廚師,基本刀功不會差;一個卓越的資料分析師,SQL功底也不會含糊。

相關文章