hive是Apache的一个顶级项目,由facebook团队开发,基于java开发面向分析师或BI等人员的数据工具(常用作数据仓库),它将hdfs文件组织成表,使用hive-sql调用mapreduce任务完成计算。即使你不知道它的内部机制也不懂java,却不影响你使用。

  这里主要以CLI使用为主,材料来源《Hive权威指南》、个人工作和网上讨论。在阅读前,希望可以先了解一下hive的安装(上一篇博客有),这对理解hive的运行机制有一定帮助。如有疑问或问题,欢迎沟通讨论。

shell执行hive

  hive命令在shell中执行有多种,可以通过hive --help --service cli进行查询具体参数,使用如下 

 #执行SQL语句
hive -e "sql语句" #可以添加-S参数,设置静默状态,不输出ok等消息 #执行SQL文件
hive -f sql_file (或者加载hive -S -f sql_file 注:S-Silence) #执行SQL文件并留在hive交互窗口
hive -i sql_file

hive中用(hadoop) shell命令

  >当我们进入hive的交互模式后,不需要像shell(hadoop fs -cmd -para dir/file)那样与hadoop文件交互,使用dfs就可以了。

    例如:当我们想看看一张表的大小时,我们首先找到这张表的位置(假设我们用desc formatted table_name我找到对应表的location)

     hive > dfs -du -s -h hdfs://usr/hive/warehouse/mydb.db/tab2

  >当我们需要执行一个hive文件时,可以使用source关键字.

    例如:hive> source /home/shj/sql_file.sql;

  >当我们希望执行一个shell之后而又不想退出hive时,可以在命令前后添加"!"和";"就可以了。

    例如:hive > ! ls /home/shj/ ;

hive中的表

  hive通过metastore实现与文件的映射。hive中的数据库其实是一个目录(该目录我们可在hive-site.xml中设置hive.metastore.warehouser.dir,假设该值我们设置为/usr/hive/warehouse,那么后期创建的数据库都是该目录的子目录),以db格式的文件。比如说我create database mydb;那么这个数据库文件就是:/usr/hive/warehouse/mydb.db,后期建的表对应文件是这个目录的子文件。

  I、hive表类型:管理表(内部表)、外部表、分区表(静态、动态)、分桶表。  (不同维度的划分)

    >内部表:我们正常建立的表属于内部表,hive管理着这个表(元数据和文件数据),我们操作该表就是操作该元数据以及文件数据。要是我们删了这个表,也就是删了这个表对应的文件

    >外部表(external):外部表类似于将hive与文件的链接(link),hive仅管理着元数据。当我们删除该表时,也只是删除数据结构,底层文件并没有被删除。

    >分区表(partition):当数据量比较大,进行查询时必然导致性能问题。而分区表,就是对大量的表文件以一个虚拟列(如地区、时间)的方式进行拆分成多个文件。指定分区进行查询时,仅扫描对应分区文件,有效提升查询性能。(查询时应指定,在不确定分区范围时将进行全分区扫描,性能差)

    >分桶表(bucket):工作中遇到的不多,会用来进行数据抽样(tablesample其实也可以用,此外两个分桶表join进行查询时效率会提升很多)。它与分区表的不同,它分桶的列是表中真实存在的列。文件组织分式与分区相似。

  II、查看表信息

    当一个表已经创建好了,我们怎么看这个表呢?(它的字段,备注,创建人,基本统计信息,文件地址等等)

    >desc [extended/formatted] mydb.tab2; desc是describe的缩写,当我们查看表时补充上extended或formatted时输出的信息将更多。推荐使用formatted,这样输出的信息相对标准化,更容易找到我们要的信息。这些信息中,Table Type如果是"MANAGED_TABLE"是内部表,"EXTERNAL_TABLE"是外部表;分区和分桶信息可以参见:Partition Infomation和Number Buckets

    >show tables  in mydb like '*tab1*';查询在mydb库中,关键字“tab1”的表名称。(这里非%)

    >set hive.cli.print.current.db=true;set hive.cli.print.header=true;第一个:显示当前库名;第二个:输出列名;

  III、hive表的创建

    创建或修改或删除都可以在语句中添加if判断来避免系统报错(if [not] exists),文章中不再说明这点。在表的创建中,我们除了指定分隔符,还可以指定表备注(COMMENT)、表属性(TBLPROPERTIES)、指定文件地址(LOCATION)等。如果想复制他表结构:create table mydb.tab2 like mydb.tab_tmp;

    >内部表:create table mydb.tab2(col1 string,col2 int,col3 bigint,...)row format delimited fields terminated by '\001' stored as textfile;(存储格式不指定时,默认以textfile;)

    >外部表:create external table mydb.tab2(col1 string,col2 int,col3 bigint,...) row format delimited fields terminated by '\001' location ‘/other/data’;(创建时便指定加载)

    >分区表:create table mydb.tab2(col1 string,...) partitioned by (year string,month string) row format delimited fields terminated by '\t';

    >分桶表:create table mydb.tab2(col1 string,...) clustered by (type) into 10 buckets row format delimited fields terminated by ',';(这里其实还需要配置一些参数,暂略)

    数据创建时,默认存储格式textfile;此外,常用的还有orcfile(通过对行记录块进行列存储并压缩,每个块提供一个存储),相比于textfile而言,对于大数据量,orcfile写入较慢,但查询和空间都比textfile更好(写入时需要启动解压缩)。下面的列表是对150万的数据进行的比照。很明显大数据量下orcfile对查询和磁盘占用更加友好。【补充:并不是所有的查询都会比textfile快】

    

  IV、hive表的修改

    >修改表名:alter table mydb.tab3 rename to mydb.tab2;

    >修改列:alter table mydb.tab2 change column col_old col_new bigint [comment'修改示例'] after other_col;

    >增加列:alter table mydb.tab2 add columns(col1 string ,col2 int.col3 bigint);

    >删除列:alter table mydb.tab2 replace columns (var1 int comment '***'  ,var2 bigint comment '***',.....)   仅保留这些字段,其他字段都将被删除

    >增减分区:alter table mydb.tab2 add(/drop) if [not] exists partition(year='17',month='02') [....] ;

  V、数据导入/导出hive

    >数据导入

      load data [local] inpath '/test/hive/data/' [overwrite] into table mydb.tab2 [partition (year='201709')];

      说明:local参数指示为本地文件,无则为hdfs文件。overwrite是否为覆盖原有【分区】数据,partition为指定分区;

        hive > load data local inpath '/home/shj/data/' into table mydb.tab_tmp;(说明,路径最好就是一个文件夹,hive将加载文件下的所有数据;对应的加载表应该已创建)

        hive > load data inpath '/hive/warehouse/data/input/' into table mydb.tab_tmp_1 partition(year='2017');(hdfs中数据就move了,不同于本地的复制;注意inpath文件夹下不能含有文件夹)

      除了load,还可以使用查询语句导入数据(hdfs)

        hive > insert into mydb.tab2 select * from mydb.tab_tmp where conditions;

        hive > create table mydb.tab2 as select * from mydb.tab_tmp where conditions;

    >数据导出

      insert overwrite [local] directory '/hive/data'  select * from mydb.tab2 where conditions;(指定local则为本地文件,directory后面后文件夹,如果没有对应路径,会自动创建)

        hive >  insert overwrite directory 'home/shj/data/export/' select * from mydb.tab2 where conditions;(导出到本地,默认列分割符为'\t'。建表时的分隔符被取代)

        hive > insert overwrite directory '/cluster/hive/warehouse/mydb.db/test/' select * from mydb.tab2 where conditions;(导出到hdfs,列分割符默认是'\001'即^A)

        此外,常用的还是用hive -e/f > /directory/filename进行数据的导出。

hive中的查询

    hql与t-sql还是有一定的差异的。这里我们谈谈join、排序和抽样。

    join:hive中的join是只支持等值链接。也就是a join b on a.c1=b.c1;不支持非等值连接。此外,hive中除了支持常用的left join /right join /full outer join,还有一种join类型:left semi-join(左半开链接)。用来返回左边表记录,只要记录满足与右边表的on条件,是对in/exists的一种优化。(join优化将在后面单独说明。)

      hive > select a.* from tab2 t1 left semi join tab_tmp t2 on t1.c1=t2.c1 and t1.c2=t2.c2;

    排序:hive中可实现排序有distritute by 、sort by、order by。distribute by是在map输出时以什么样的方式到reduce中(多个reduce,根据什么key);sort by 是reduce完成后,单个reduce怎么将结果进行排序;order by是全局的排序,在一个reduce中完成。当数据量大时,order by将耗时较长。可以先指定distribute by 后指定sort by。实现输出的结果根据某些字段排序。当distribute by与sort by的字段相同时,则等同于cluster by。

      hive > select * from tab2 distribute by c1,c2 sort by c1;

      hive > select * from tab2 cluster by c1;

    抽样:当数据很大时,就避免不了抽样。在hive中关键字tablesample实现,一种分桶抽样,一种数据块抽样。

      hive > select * from mydb.tab2 tablesample(bucket 12 out of 1000 on rand()) s;(分母是分桶数,分子是指定桶序号;关键字rand()保障随机性,即同样两次抽样结果不同)

      hive > select * from mydb.tab2 tablesample(0.02 percent) s;(百分比抽样,这里相当于10000中取2个)

hive参数调整

    hive中的参数常常用于调优,设定map/reduce数,map-join,block大小,是否本地化等等。这个我们会在后期进行探讨和沟通。现在我们看看,使用CLI端,有哪些设置让操作更加舒适

    > set hive.cli.print.header=true;设置输出是否带有表头(当我们输出文件时,没有表头可能对导入数据库和阅读带来一定影响。这个参数完美解决这个问题。)

    > set hive.cli.print.current.db=true;显示当前数据库位置(可以使用use database;进行数据库切换)

    > set hive.exec.parallel=true;允许任务并行,可以提高我们查询效率

未完待续!

原创博客,转载请注明出处!欢迎邮件沟通:shj8319@sina.com

别只用hive写sql -- hive的更多技能的更多相关文章

  1. 写好Hive 程序的若干优化技巧和实际案例

    使用Hive可以高效而又快速地编写复杂的MapReduce查询逻辑.但是一个”好”的Hive程序需要对Hive运行机制有深入的了解,像理解mapreduce作业一样理解Hive QL才能写出正确.高效 ...

  2. hive(II)--sql考查的高频问题

    在了解别人hive能力水平的时候,不管是别人问我还是我了解别人,有一些都是必然会问的东西.问的问题也大都大同小异.这里总结一下我遇到的那些hive方面面试可能涉及的问题 1.行转列(列转行) 当我们建 ...

  3. 【翻译】Flink Table Api & SQL — Hive —— 读写 Hive 表

    本文翻译自官网:Reading & Writing Hive Tables  https://ci.apache.org/projects/flink/flink-docs-release-1 ...

  4. 【翻译】Flink Table Api & SQL — Hive Beta

    本文翻译自官网:Hive Beta https://ci.apache.org/projects/flink/flink-docs-release-1.9/dev/table/hive/ Flink ...

  5. hive Hbase sql

    Hive和HBase的区别 ​ hive是为了简化编写MapReduce程序而生的,使用MapReduce做过数据分析的人都知道,很多分析程序除业务逻辑不同外,程序流程基本一样.在这种情况下,就需要h ...

  6. [Hive - LanguageManual ] ]SQL Standard Based Hive Authorization

    Status of Hive Authorization before Hive 0.13 SQL Standards Based Hive Authorization (New in Hive 0. ...

  7. 【HIVE】sql语句转换成mapreduce

    1.hive是什么? 2.MapReduce框架实现SQL基本操作的原理是什么? 3.Hive怎样实现SQL的词法和语法解析? 连接:http://www.aboutyun.com/thread-20 ...

  8. Hive执行sql文件

    方法1: hive -f sql文件 t.sql文件内容: ; 执行命令 hive -f t.sql 方法2: 进入hive shell, 执行source命令 进入hive 终端 $ hive hi ...

  9. [Spark][Hive][Python][SQL]Spark 读取Hive表的小例子

    [Spark][Hive][Python][SQL]Spark 读取Hive表的小例子$ cat customers.txt 1 Ali us 2 Bsb ca 3 Carls mx $ hive h ...

随机推荐

  1. Redis-rdb持久化

    Redis实现快照的过程 redis调用fork,现在有了子进程和父进程 父进程继续处理client请求,子进程负责将内存内容写入到临时文. 由于os的写时复制机制(copy on write)父子进 ...

  2. pick定理详解

    一.概念 假设P的内部有I(P)个格点,边界上有B(P)个格点,则P的面积A(P)为:A(P)=I(P)+B(P)/2-1. 二.说明 Pick定理主要是计算格点多边形(定点全是格点的不自交图形)P的 ...

  3. C#之异步

    C#之异步 异步是相对于同步而言.跟多线程不能同一而论.异步简单而言好比一个人两双手可以同时做两件以上不同的事情.多线程好比多个人做不同或相同的事情. 异步跟多线程有什么关系? 异步可以分为CPU异步 ...

  4. CentOS 常用命令及快捷键整理

    常用命令: 文件和目录: # cd /home                        进入 '/home' 目录 # cd ..                                ...

  5. 超超超简单的bfs——POJ-3278

    Catch That Cow Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 89836   Accepted: 28175 ...

  6. NYOJ--257--郁闷的C小加(一)(中缀表达式变后缀表达式 )

    郁闷的C小加(一) 时间限制:1000 ms  |  内存限制:65535 KB 难度:3   描述 我们熟悉的表达式如a+b.a+b*(c+d)等都属于中缀表达式.中缀表达式就是(对于双目运算符来说 ...

  7. let const 下篇

    1.不存在变量提升 在之前的js代码中,声明一个变量或者是函数,会存在变量提升的现象,也就是说变量可以在声明之前使用,值为undefined: es5: console.log(a); //undef ...

  8. Dbentry4.2连接MSSQL

    Dbentry4.2 连接MSSQL <Leafing.Settings> <add key="DefaultContext" value="mssql ...

  9. JQuery中的回调对象

    JQuery中的回调对象 回调对象(Callbacks object)模块是JQuery中的一个很基础的模块,很多其他的模块(比如Deferred.Ajax等)都依赖于Callbacks模块的实现.本 ...

  10. Web存储—简易注册登录

    Web Storage是HTML5引入的一个非常重要的功能,可以在客户端本地存储数据,类似HTML4的cookie,但可实现功能要比cookie强大的多,cookie大小被限制在4KB,cookie只 ...