Hive本質是將SQL轉換為MapReduce的任務進行運算,底層由HDFS來提供資料儲存,說白了hive可以理解為一個將SQL轉換為MapReduce的任務的工具,甚至更近一步說hive就是一個MapReduce使用者端。
如果直接使用hadoop的話,人員學習成本太高,專案要求週期太短,MapReduce實現複雜查詢邏輯開發難度太大。如果使用hive的話,可以操作介面採用類SQL語法,提高開發能力,免去了寫MapReduce,減少開發人員學習成本,功能擴充套件很方便(比如:開窗函數)。
1、可延伸性
Hive可以自由的擴充套件叢集的規模,一般情況下不需要重啟服務
2、延申性
Hive支援自定義函數,使用者可以根據自己的需求來實現自己的函數
3、容錯
即使節點出現錯誤,SQL仍然可以完成執行
優點:
1、操作介面採用類sql語法,提供快速開發的能力(簡單、容易上手)
2、避免了去寫MapReduce,減少開發人員的學習成本
3、Hive的延遲性比較高,因此Hive常用於資料分析,適用於對實時性要求不高的場合
4、Hive 優勢在於處理巨量資料,對於處理小資料沒有優勢,因為 Hive 的執行延遲比較高。(不斷地開關JVM虛擬機器器)
5、Hive 支援使用者自定義函數,使用者可以根據自己的需求來實現自己的函數。
6、叢集可自由擴充套件並且具有良好的容錯性,節點出現問題SQL仍可以完成執行
缺點:
1、Hive的HQL表達能力有限
(1)迭代式演演算法無法表達 (反覆呼叫,mr之間獨立,只有一個map一個reduce,反覆開關)
(2)資料探勘方面不擅長
2、Hive 的效率比較低
(1)Hive 自動生成的 MapReduce 作業,通常情況下不夠智慧化
(2)Hive 調優比較困難,粒度較粗 (hql根據模板轉成mapreduce,不能像自己編寫mapreduce一樣精細,無法控制在map處理資料還是在reduce處理資料)
紀錄檔分析:大部分網際網路公司使用hive進行紀錄檔分析,如百度、淘寶等。
統計一個網站一個時間段內的PV(頁面瀏覽量)UV(統計一天內某站點的使用者數)SKU ,SPU
Hive允許client連線的方式有三個CLI(hive shell)、JDBC/ODBC(java存取hive)、WEBUI(瀏覽器存取 hive)。JDBC存取時中介軟體Thrift軟體框架,跨語言服務開發。DDL DQL DML,整體仿寫一套SQL語句。
1)client–需要下載安裝包
2)JDBC/ODBC 也可以連線到Hive
現在主流都在倡導第二種 HiveServer2/beeline
做基於使用者名稱和密碼安全的一個校驗
3)Web Gui
hive給我們提供了一套簡單的web頁面
我們可以通過這套web頁面存取hive 做的太簡陋了
後設資料包括表名、表所屬的資料庫(預設是default)、表的擁有者、列/分割區欄位、表的型別(是否是 外部表)、表的資料所在目錄等。
一般需要藉助於其他的資料載體(資料庫)
主要用於存放資料庫的建表語句等資訊
推薦使用Mysql資料庫存放資料
連線資料庫需要提供:uri username password driver
後設資料儲存在資料庫中,預設存在自帶的derby資料庫(單使用者侷限性)中,推薦使用Mysql進行儲存。
1) 解析器(SQL Parser):將SQL字串轉換成抽象語法樹AST,這一步一般都用第三方工具庫完 成,比如ANTLR;對AST進行語法分析,比如表是否存在、欄位是否存在、SQL語意是否有誤。
2) 編譯器(Physical Plan):將AST編譯生成邏輯執行計劃。
3) 優化器(Query Optimizer):對邏輯執行計劃進行優化。
4) 執行器(Execution):把邏輯執行計劃轉換成可以執行的物理計劃。對於Hive來說,就是 MR/Spark。
Hive的資料儲存在HDFS中,計算由MapReduce完成。HDFS和MapReduce是原始碼級別上的整合,兩者結合最佳。直譯器、編譯器、優化器完成HQL查詢語句從詞法分析、語法分析、編譯、優化以及查詢計劃的生成。
shell互動Hive,用命令hive啟動一個hive的shell命令列,在命令列中輸入sql或者命令來和Hive互動。
伺服器端啟動metastore服務(後臺啟動):nohup hive --service metastore >/dev/null &
進入命令:hive
退出命令列:quit;
Hive啟動為一個伺服器,對外提供服務,其他機器可以通過使用者端通過協定連線到伺服器,來完成存取操作,這是生產環境用法最多的
伺服器端啟動hiveserver2服務:
nohup hive --service metastore >/dev/null &
nohup hiveserver2 >/dev/null &
需要稍等一下,啟動服務需要時間:
進入命令:1)先執行: beeline ,再執行: !connect jdbc:hive2://master:10000
2)或者直接執行: beeline -u jdbc:hive2://master:10000 -n root
退出命令列:!exit
使用 –e 引數來直接執行hql的語句
bin/hive -e "show databases;"
使用 –f 引數通過指定文字檔案來執行hql的語句
特點:執行完sql後,回到linux命令列。
建立一個sql檔案:vim hive.sql
裡面寫入要執行的sql命令
use myhive;
select * from test;
hive -f hive.sql
Hive後設資料庫中一些重要的表結構及用途,方便Impala、SparkSQL、Hive等元件存取後設資料庫的理解。
1、儲存Hive版本的後設資料表(VERSION),該表比較簡單,但很重要,如果這個表出現問題,根本進不來Hive-Cli。比如該表不存在,當啟動Hive-Cli的時候,就會報錯「Table 'hive.version' doesn't exist」
2、Hive資料庫相關的後設資料表(DBS、DATABASE_PARAMS)
DBS:該表儲存Hive中所有資料庫的基本資訊。
DATABASE_PARAMS:該表儲存資料庫的相關引數。
3、Hive表和檢視相關的後設資料表
主要有TBLS、TABLE_PARAMS、TBL_PRIVS,這三張表通過TBL_ID關聯。
TBLS:該表中儲存Hive表,檢視,索引表的基本資訊。
TABLE_PARAMS:該表儲存表/檢視的屬性資訊。
TBL_PRIVS:該表儲存表/檢視的授權資訊。
4、Hive檔案儲存資訊相關的後設資料表
主要涉及SDS、SD_PARAMS、SERDES、SERDE_PARAMS,由於HDFS支援的檔案格式很多,而建Hive表時候也可以指定各種檔案格式,Hive在將HQL解析成MapReduce時候,需要知道去哪裡,使用哪種格式去讀寫HDFS檔案,而這些資訊就儲存在這幾張表中。
SDS:該表儲存檔案儲存的基本資訊,如INPUT_FORMAT、OUTPUT_FORMAT、是否壓縮等。TBLS表中的SD_ID與該表關聯,可以獲取Hive表的儲存資訊。
SD_PARAMS: 該表儲存Hive儲存的屬性資訊。
SERDES:該表儲存序列化使用的類資訊。
SERDE_PARAMS:該表儲存序列化的一些屬性、格式資訊,比如:行、列分隔符。
5、Hive表欄位相關的後設資料表
主要涉及COLUMNS_V2:該表儲存表對應的欄位資訊。
資料庫在hdfs上的預設路徑是/hive/warehouse/*.db
create database testdb;
避免要建立的資料庫已經存在錯誤,增加if not exists判斷。(標準寫法)
create database if not exists testdb;
建立資料庫並指定位置
create database if not exists testdb location '/testdb.db';
資料庫的其他後設資料資訊都是不可更改的,包括資料庫名和資料庫所在的目錄位置。
alter database dept set dbproperties('createtime'='20220531');為資料庫的DBPROPERTIES設定鍵值對屬性值
顯示資料庫
show databases;
通過like過濾顯示資料庫
show datebases like '*t*';(這裡是*,sql裡是%)
檢視資料庫詳情
desc database testdb;
切換資料庫
use testdb;
最簡寫法
drop database testdb;
如果刪除的資料庫不存在,最好使用if exists判斷資料庫是否存在。否則會報錯:FAILED: SemanticException [Error 10072]: Database does not exist: db_hive
drop database if exists testdb;
如果資料庫不為空,使用cascade命令進行強制刪除。報錯資訊如下FAILED: Execution Error, return code 1 from org.apache.hadoop.hive.ql.exec.DDLTask. InvalidOperationException(message:Database db_hive is not empty. One or more tables exist.)
drop database if exists testdb cascade;
型別 | Java資料型別 | 描述 |
---|---|---|
TINYINT | byte | 8位元有符號整型。取值範圍:-128~127。 |
SMALLINT | short | 16位元有符號整型。取值範圍:-32768~32767。 |
INT | int | 32位元有符號整型。取值範圍:-2 31 ~2 31 -1。 |
BIGINT | long | 64位元有符號整型。取值範圍:-2 63 +1~2 63 -1。 |
BINARY | 二進位制資料型別,目前長度限制為8MB。 | |
FLOAT | float | 32位元二進位制浮點型。 |
DOUBLE | double | 64位元二進位制浮點型。 |
DECIMAL(precision,scale) | 10進位制精確數位型別。precision:表示最多可以表示多少位的數位。取值範圍:1 <= precision <= 38。scale:表示小數部分的位數。取值範圍: 0 <= scale <= 38。如果不指定以上兩個引數,則預設為decimal(10,0)。 | |
VARCHAR(n) | 變長字元型別,n為長度。取值範圍:1~65535。 | |
CHAR(n) | 固定長度字元型別,n為長度。最大取值255。長度不足則會填充空格,但空格不參與比較。 | |
STRING | string | 字串型別,目前長度限制為8MB。 |
DATE | 日期型別,格式為yyyy-mm-dd 。取值範圍:0000-01-01~9999-12-31。 |
|
DATETIME | 日期時間型別。取值範圍:0000-01-01 00:00:00.000~9999-12-31 23.59:59.999,精確到毫秒。 | |
TIMESTAMP | 與時區無關的時間戳型別。取值範圍:0000-01-01 00:00:00.000000000~9999-12-31 23.59:59.999999999,精確到納秒。說明 對於部分時區相關的函數,例如cast( as string),要求TIMESTAMP按照與當前時區相符的方式來展現。 | |
BOOLEAN | boolean | BOOLEAN型別。取值:True、False。 |
型別 | 定義方法 | 構造方法 |
---|---|---|
ARRAY | array<int>``array<struct<a:int, b:string>> |
array(1, 2, 3)``array(array(1, 2), array(3, 4)) |
MAP | map<string, string>``map<smallint, array<string>> |
map(「k1」, 「v1」, 「k2」, 「v2」)``map(1S, array(‘a’, ‘b’), 2S, array(‘x’, ‘y’)) |
STRUCT | struct<x:int, y:int>struct<field1:bigint, field2:array<int>, field3:map<int, int>> named_struct(‘x’, 1, ‘y’, 2) named_struct(‘field1’, 100L, ‘field2’, array(1, 2), ‘field3’, map(1, 100, 2, 200)) |
Hive有三種複雜資料型別ARRAY、MAP 和 STRUCT。ARRAY和MAP與Java中的Array和Map類似,而STRUCT與C語言中的Struct類似,它封裝了一個命名欄位集合,複雜資料型別允許任意層次的巢狀。還有一個uniontype< 所有型別,所有型別… > 。
陣列:array< 所有型別 >;
Map < 基本資料型別,所有資料型別 >;
struct < 名:所有型別[註釋] >;
uniontype< 所有型別,所有型別… >
Hive沒有專門的資料檔案格式,常見的有以下幾種:
TEXTFILE:Hive預設檔案儲存格式
SEQUENCEFILE
AVRO
RCFILE:列檔案格式,能夠很好的壓縮和快速查詢效能
ORCFILE:很高的壓縮比,能很大程度的節省儲存和計算資源,但它在讀寫時候需要消耗額外的CPU資源來壓縮和解壓縮
PARQUET
CREATE [EXTERNAL] TABLE [IF NOT EXISTS] table_name
[(col_name data_type [COMMENT col_comment], ...)]
[COMMENT table_comment]
[PARTITIONED BY (col_name data_type [COMMENT col_comment], ...)]
[CLUSTERED BY (col_name, col_name, ...)
[SORTED BY (col_name [ASC|DESC], ...)] INTO num_buckets BUCKETS]
[ROW FORMAT row_format]
[STORED AS file_format]
[LOCATION hdfs_path]
欄位解釋說明:
- CREATE TABLE
建立一個指定名字的表。如果相同名字的表已經存在,則丟擲異常;使用者可以用 IF NOT EXISTS 選項來忽略這個異常。
- EXTERNAL
關鍵字可以讓使用者建立一個外部表,在建表的同時指定一個指向實際資料的路徑(LOCATION)
建立內部表時,會將資料移動到資料倉儲指向的路徑(預設位置);
建立外部表時,僅記錄資料所在的路徑,不對資料的位置做任何改變。在
刪除表的時候,內部表的後設資料和資料會被一起刪除,而外部表只刪除後設資料,不刪除資料。
- COMMENT:
為表和列新增註釋。
- PARTITIONED BY
建立分割區表
- CLUSTERED BY
建立分桶表
- SORTED BY
不常用
- ROW FORMAT
DELIMITED [FIELDS TERMINATED BY char] [COLLECTION ITEMS TERMINATED BY char] [MAP KEYS TERMINATED BY char] [LINES TERMINATED BY char] | SERDE serde_name [WITH SERDEPROPERTIES (property_name=property_value, property_name=property_value, ...)]
使用者在建表的時候可以自定義SerDe或者使用自帶的SerDe。
如果沒有指定ROW FORMAT 或者ROW FORMAT DELIMITED,將會使用自帶的SerDe。
在建表的時候,使用者還需要為表指定列,使用者在指定表的列的同時也會指定自定義的SerDe,Hive通過SerDe確定表的具體的列的資料。
SerDe是Serialize/Deserilize的簡稱,目的是用於序列化和反序列化。
- STORED AS指定儲存檔案型別
常用的儲存檔案型別:SEQUENCEFILE(二進位制序列檔案)、TEXTFILE(文字)、RCFILE(列式儲存格式檔案)
如果檔案資料是純文字,可以使用STORED AS TEXTFILE。
如果資料需要壓縮,使用 STORED AS SEQUENCEFILE。
- LOCATION :
指定表在HDFS上的儲存位置。
- LIKE
允許使用者複製現有的表結構,但是不復制資料。
create table students
(
id bigint,
name string,
age int,
gender string,
clazz string
)
ROW FORMAT DELIMITED FIELDS TERMINATED BY ','; // 必選,指定列分隔符
create table students2
(
id bigint,
name string,
age int,
gender string,
clazz string
)
ROW FORMAT DELIMITED FIELDS TERMINATED BY ','
LOCATION '/input1'; // 指定Hive表的資料的儲存位置,一般在資料已經上傳到HDFS,想要直接使用,會指定Location,通常Locaion會跟外部表一起使用,內部表一般使用預設的location
create table students3
(
id bigint,
name string,
age int,
gender string,
clazz string
)
ROW FORMAT DELIMITED FIELDS TERMINATED BY ','
STORED AS rcfile; // 指定儲存格式為rcfile
如果不指定,預設為textfile,注意:除textfile以外,其他的儲存格式的資料都不能直接載入,需要使用從表載入的方式。
create table students4 as select * from students2;
create table students5 like students;
create table IF NOT EXISTS t_person(
name string,
friends array<string>,
children map<string,int>,
address struct<street:string ,city:string>
)
row format delimited fields terminated by ','
collection items terminated by '_'
map keys terminated by ':'
lines terminated by '\n';
songsong,bingbing_lili,xiao song:18_xiaoxiao song:19,beng bu_anhui
yangyang,caicai_susu,xiao yang:18_xiaoxiao yang:19,he fei_anhui
show tables;
show tables like 'u';
desc t_person;
desc formatted t_person;
load data inpath '/input1/students.txt' into table students;
將HDFS上的/input1目錄下面的資料 移動至 students表對應的HDFS目錄下,注意是 移動、移動、移動
load data local inpath '/usr/local/soft/data/students.txt' into table students;
load data local inpath '/usr/local/soft/data/students.txt' overwrite into table students;
truncate table students;
將 students表的資料插入到students2 這是複製 不是移動 students表中的表中的資料不會丟失
insert into table students2 select * from students;
覆蓋插入 把into 換成 overwrite
insert overwrite table students2 select * from students;
查詢表結構
desc students2;
新增列
alter table students2 add columns (education string);
查詢表結構
desc students2;
更新列
alter table stduents2 change education educationnew string;
drop table students2;
建立好表的時候,HDFS會在當前表所屬的庫中建立一個資料夾
當load資料的時候,就會將資料檔案存放到表對應的資料夾中
資料一旦被load,就不能被修改
刪除表的時候,表對應的資料夾會被刪除,同時資料也會被刪除
預設建表的型別就是內部表
外部表因為是指定其他的hdfs路徑的資料載入到表中來,所以hive會認為自己不完全獨佔這份資料
刪除hive表的時候,資料仍然儲存在hdfs中,不會刪除。
外部表關鍵字external
一般在公司中,使用外部表多一點,因為資料可以需要被多個程式使用,避免誤刪,通常外部表會結合location一起使用
外部表還可以將其他資料來源中的資料 對映到 hive中,比如說:hbase,ElasticSearch......
設計外部表的初衷就是 讓 表的後設資料 與 資料 解耦
將表中的資料備份
//建立存放資料的目錄
mkdir -p /usr/local/soft/shujia
//匯出查詢結果的資料(匯出到Node01上)
insert overwrite local directory '/usr/local/soft/shujia/person_data' select * from t_person;
-- 建立存放資料的目錄
mkdir -p /usr/local/soft/shujia
-- 匯出查詢結果的資料
insert overwrite local directory '/usr/local/soft/shujia/person'
ROW FORMAT DELIMITED fields terminated by ','
collection items terminated by '-'
map keys terminated by ':'
lines terminated by '\n'
select * from t_person;
-- 建立存放資料的目錄
hdfs dfs -mkdir -p /shujia/bigdata17/copy
-- 匯出查詢結果的資料
insert overwrite local directory '/usr/local/soft/shujia/students_data2' ROW FORMAT DELIMITED FIELDS TERMINATED BY ',' select * from students
// 建立存放資料的目錄
hdfs dfs -mkdir -p /shujia/bigdata17/person
// 使用HDFS命令拷貝檔案到其他目錄
hdfs dfs -cp /hive/warehouse/t_person/* /shujia/bigdata17/person
將表結構和資料同時備份
將資料匯出到HDFS
//建立存放資料的目錄
hdfs dfs -mkdir -p /shujia/bigdata17/copy
//匯出查詢結果的資料
export table t_person to '/shujia/bigdata17/copy';
刪除表結構
drop table t_person;
恢復表結構和資料
import from '/shujia/bigdata17';
注意:時間不同步,會導致匯入匯出失敗