Hive:分区原因、创建分区、静态分区 、动态分区

x33g5p2x  于2021-11-21 转载在 Hive  
字(2.6k)|赞(0)|评价(0)|浏览(840)

① Hive 数据管理、内外表、安装模式操作

② Hive:用SQL对数据进行操作,导入数据、清洗脏数据、统计数据订单

③ Hive:多种方式建表,需求操作

④ Hive:分区原因、创建分区、静态分区 、动态分区

⑤ Hive:分桶的简介、原理、应用、创建

⑥ Hive:优化 Reduce,查询过程;判断数据倾斜,MAPJOIN

1、为什么要分区?

1、在Hive Select查询中一般会扫描整个表内容,会消耗很多时间做没必要的工作。有时候只需要扫描表中关心的一部分数据,因此建表时引入了partition概念。

2、分区表指的是在创建表时指定的partition的分区空间。

3、如果需要创建有分区的表,需要在create表的时候调用可选参数partitioned by。

2、如何分区以及细节

根据业务分区,(完全看业务场景)选取id、年、月、日、男女性别、年龄段 或者是能平均将数据分到不同文件中最好,分区不好将直接导致查询结果延迟。

分区细节:

  • 一个表可以拥有一个或者多个分区,每个分区以文件夹的形式单独存在表文件夹的目录下;
  • 表和列名不区分大小写;
  • 分区是以字段的形式在表结构中存在,但是该字段不存放实际的数据内容,仅仅是分区的表示;
  • 分区有一级、二级设置一般设置为一级分区;
  • 分区分为动态分区和静态分区。

3、创建分区

接着上一篇博文用的数据 udata,进行分区操作。

-- 1、创建分区,分区字段为 dt
CREATE TABLE `udata_partition`(
  `user_id` string, 
  `item_id` string, 
  `rating` int)
PARTITIONED BY (`dt` string)
ROW FORMAT DELIMITED 
  FIELDS TERMINATED BY '\t' 
  LINES TERMINATED BY '\n' 

-- 2、查看表结构
show create table udata_partition ;  
desc udata_partition ;

4、静态分区

每个分区要写一个load data,缺点:load data 效率低下,非常繁琐,不常用静态分区在业务中。

应用场景: 数据量不大,同时要知道分区的数据类型

--1、静态分区设置
insert overwrite table udata_partition partition (dt='2021-11-10')
select user_id, item_id, rating from udata where user_id='242';

--2、查看分区
show partitions udata_partition;

--3、查看udata_partition数据
select * from udata_partition;

-- 1、再插入数据
insert overwrite table udata_partition partition (dt='2021-11-11')
select user_id, item_id, rating from udata where user_id='222';
--2、查看分区
show partitions udata_partition;
--3、查看udata_partition数据
select * from udata_partition;

我们再去HDFS目录查看。在udata_partition文件有是否有两个分区文件。

-- 1、查看udata_partition文件目录下的文件是否是那两个分区
hadoop fs -ls  /user/hive/warehouse/badou.db/udata_partition/

-- 2、查看分区文件:dt=2021-11-10 下的文件
hadoop fs -ls  /user/hive/warehouse/badou.db/udata_partition/dt=2021-11-10

-- 3、cat dt=2021-11-10文件里的数据。
hadoop fs -cat  /user/hive/warehouse/badou.db/udata_partition/dt=2021-11-10/00*

上图数据显示结果 == select user_id, item_id, rating from udata where user_id=‘242’; 保存的分区文件。

5、动态分区

应用场景: 不确定分区数量,数据量也不是很大,使用动态分区
实际工作中趋向于使用动态分区!!!

--注意:以下设置,只在当前的会话窗口有效
-- 1.打开动态分区模式:
set hive.exec.dynamic.partition=true;
-- 2.设置分区模式为非严格模式
set hive.exec.dynamic.partition.mode=nonstrict;

我们知道udata的内容,我们要把时间戳转为年月日,与上面静态分区的格式一致。

-- 1、把时间戳case为 bigint
cast(`timestamp` as bigint)
-- 2、from_unixtime()是实现格式转换
from_unixtime(cast(`timestamp` as bigint), 'yyyy-MM-dd HH:mm:ss')
-- 3、显示结果
select user_id, item_id, rating, from_unixtime(cast(`timestamp` as bigint), 'yyyy-MM-dd HH:mm:ss') from udata limit 15;

我们不需要时分秒,用to_data(from_unixtime(...)) as res

-- 4、取消时分秒
select user_id, item_id, rating, to_date(from_unixtime(cast(`timestamp` as bigint), 'yyyy-MM-dd HH:mm:ss')) from udata limit 15;

实现分区动态加载:

insert overwrite table udata_partition partition (dt)
select user_id, item_id, rating,
to_date(from_unixtime(cast(`timestamp` as bigint), 'yyyy-MM-dd HH:mm:ss')) 
as res from udata
where user_id='22';
-- udata_partition dt数据=res数据;

相关文章