Hive笔记(一)

Hive将Sql查询转化为一系列在hadoop集群上运行的MapReduce作业。

 

create table records (year string, temperature int, quality int)

row format delimited   说明文本是按行分割的,也可使用serde字句来指定所使用的工具

fields terminated by '\t';  行分隔符为制表符

 

选项                       默认值            作用

hive.metastore.warehouse.dir     /user/hive/warehouse    仓库目录

javax.jdo.option.ConnectionURL       jdbc:mysql://host/dbname?

javax.jdo.option.ConnectionDrivername    com.mysql.jdbc.Driver

 

配置:

hive --config /user/hadoop/hive-0.9.0/conf/hive-site.xml

指定配置目录

hive -hiveconfig fs.default.name=localhost -hiveconf mapred.job.tracker=lcoalhost:8021

为单个会话配置属性,使用一个伪分布集群

hive>set hive.enforce.bucketing=true;

set命令更改设置,对于某个特定的查询修改和MapReduce作业很有用,不加参数会显示现在的值

set -v 列出所有属性的值,包括Hadoop的默认值

 

show functions    获取函数列表

show function length  函数的详细说明

create external table external_table (dummy string)

location ''; 

load data inpath '' into table external_table; 创建外部表,  删除时只会删除元数据,不会删除数据。

如果所有的数据都由Hive来处理,那么就应该建立托管表,相反,如果Hive和其他工具处理同一个数据集,那么应该建立外部表,

普遍的做法是把存放在HDFS(由其他进程创建)的初始数据集用作外部表,然后用HIVE的变换功能把数据移到托管的Hive表。这一做法反之也成立,外部表(未必在HDFS中)可以用于从Hive导出数据供其他应用程序使用。需要使用外部表的另一个原因是你想为同一数据集关联不同的模式。

分区:

create table logs (ts bigint, line string)

partitioned by (dt string, country string);

 

load data local inpath '' into table logs

partition (dt='',country='');

 

select ts,line,dt

from logs

where country='';

 

桶:

连接两个在相同列上划分了桶的表,可以使用map端连接高效的实现。

create table bucketed-users (id int, name string)

clustered by (id) into 4 buckets;

Hive 使用对值进行哈希然后在除以桶的个数取余数,这样id相同的行会被分到相同的桶内。

桶内数据可以进行排序:

create table bucketed_users (id int,name string)

clustered by (id) sorted by (id asc) into 4 buckets;

下面详细解析下分桶的过程:

首先

Hive>set hive.enforce.bucketing=true  否则不会分桶处理当插入数据的时候

create table bucketed_users (id int,name string)

clustered by (id) sorted by (id asc) into 4 buckets;

 创建一个users表:

create table users (id int, name string)

row format delimited

fields terminated by '\t';

将数据导入users表:

load data local inpath '/home/hadoop/users' into table users;

将users表中数据插入bucketed_users:(动态插入,后面会介绍

insret overwrite table bucketed_users

select * from users;

将会运行一个mapreduce作业,然后查看分桶情况:

dfs -ls /user/hive/warehouse/bucketed_users;

出现4个文件:(因为桶的个数为4)

000000_0

000001_0

000002_0

000003_0

dfs -cat 可以查看每个文件的内容。

hive>select * from bucketed_users

   tablesample(bucket 1 out of 4 on id);

用tablesample字句对表进行取样,只查询一部分桶,而不是整个表,相反,在没有桶的表中取样会查询真个表:

hive>select * from users

   tablesample(bucket 1 out of 4 on rand());

 存储格式:

Serde(序列化和反序列化工具)定义Hive中的“行格式”。

序列化:执行insect、ctas操作的时候执行序列化工作,Serde会把Hive的数据内部表示形式序列化成字节形式写入输出文件中去。

反序列化:当执行查询操作的时候,Serde会把文件中字节形式的数据行反序列化为Hive内部操作数据行时所使用的对象形式。

“文件格式”:最简单的是纯文本格式,也可以是面向行和面向列的二进制格式。也就是使用stored as的时候发生的事情,默认是文本文件。

行内默认分隔符ctrl+A,

集合默认分隔符ctrl+B(数组,map键值对,struct)

二进制存储格式:顺序文件和RCFile

create table的时候使用stored as sequencefile即可使用顺序文件。

使用顺序文件存储hive中产生的表时,一行将作为顺序文件的一条记录来存储。

面向行的存储格式对于那些只访问表中一部分行的查询比较有效,面向列的存储格式适用于行中有很多列的情况。

create table ..

row format serde 'org.......ColumnarSedde'

stored as rcfile;

以上创建的表使用面向列的存储,在创建过程中指定了面向列的Serde。

总结:

fields terminated by '\t' 前面必须跟着 row format delimited 否则会出错。

创建表的时候没有指定行内分隔符,使用load data的方式导入数据,在select的时候出行类型检查会出错,显示NULL  Null

创建表的时候没有指定行内分隔符,但采用insert的动态插入方式导入数据的话,不会出错。

Hive内部使用一个叫做lazySimpleSerde的Serde来处理分割格式,是文本格式,采用这种格式有很多的好处(Mapreduce程序和Streaming处理起来很容易,)但也可以采用一些高效紧凑的二进制Serde。

posted on 2013-04-14 23:14  waxili  阅读(591)  评论(0编辑  收藏  举报

导航