【大数据】Hadoop里的“MySQL”——Hive,干货满满

【大数据】Hadoop里的“MySQL”——Hive,干货满满

  • 文章脉络
  • Hive架构
  • HQL
    • 表类型
    • 创建表语法
    • 分区
    • 数据导入导出
  • 函数
    • 内置函数
    • UDF
      • Java
      • Python

在阅读本文前,请确保已经对Hadoop的三大组件(HDFS、MapReduce、YARN)有所了解,如果不太了解的可以移步《深入浅出Hadoop》观看。

如果仅使用MapReduce来操作HDFS中存放的数据,那么学习成本和开发成本都会比较高。于是,Hive的提出就向广大开发者提供了一种利用SQL来查询和计算HDFS文件的方法。


文章脉络

在这里插入图片描述

图1 Hive知识点脑图

Hive架构

  Hive作为Hadoop生态系统中的重要一员,它本质上是一个数仓工具。其核心功能是将存储在Hadoop分布式文件系统(HDFS)上的结构化数据文件映射为数据库中的表结构。这一映射过程允许用户通过一种类似SQL的查询语言——即Hive Query Language(HQL)——来执行数据查询和管理操作,极大地简化大数据的处理流程。

  在Hadoop生态系统中,数据文件通常以原始格式存放在HDFS上。如果我们想要对这些数据进行查询和计算,按照传统方法,我们需要编写复杂的MapReduce程序。MapReduce作为一种编程模型,虽然功能强大,但其学习成本较高,编写和维护MapReduce脚本的难度较大,这无疑增加了学习成本和时间成本,对于非程序员或数据分析人员来说尤其如此。

  Hive的出现,为大数据处理提供了一种更加简便的方法。它允许用户使用类似SQL的语句来查询数据,而这些SQL语句在Hive内部会被转换成相应的MapReduce程序。这意味着,有了Hive,即使是不熟悉MapReduce编程的用户也可以轻松地执行复杂的数据分析任务,无需直接编写繁琐的MapReduce代码。

【注意】:尽管Hive在Hadoop生态系统中扮演着重要角色,但它的定位主要是作为一个数据仓库工具,而不是一个需要独立集群部署的服务。它只是一个把SQL解释成MapReduce代码然后提交任务的工具,是不需要集群部署的

  在架构上,Hive的底层仍然依赖于MapReduce计算框架、YARN资源管理器和HDFS文件系统。需要注意的是,虽然HQL与标准SQL在语法上有很多相似之处,但它并不是完全兼容SQL的。Hive的SQL方言因包含一些特有的功能和限制,因此被称为HQL。

【注意】:不知道大家开发Java Web项目的时候有没有用过SSH架构?Hibernate与MyBatis是地位等同的框架, 当时基于Hibernate开发的SQL一度也称为HQL,注意不要与Hive SQL的简称HQL弄混了。

  HQL和SQL在设计和语法上都有一些差异,可以理解为它们俩有交集(这个交集其实就是大家平常最通用的功能,比如select * from table)。HQL不支持事务但是在查询的写法上比较强大,而SQL面向事务性数据库设计,适用于实时操作,但是写法不像HQL这么五花八门。

请添加图片描述

图2 Hive架构图

  在图2中,我们可以看到一个清晰的架构视图,其中4个最重要的组件如下:

  1、用户接口Client:Hive提供了多种用户接口,以适应不同用户的需求和使用场景。

  首先是CLI(命令行接口),它允许用户通过命令行直接与Hive交互,执行HQL语句和查看查询结果。
  其次是JDBC/ODBC接口,这使得Hive能够被任何支持JDBC或ODBC标准的第三方应用程序所访问,比如商业智能(BI)工具和定制的数据分析应用程序。

【注意】:BI,Business Intelligence,一般是公司内部部门下的一个团队,负责处理部门内部数据与外部对接、数据可视化等等。比如你是某公司外卖事业部的开发人员,想要获取你司单车部门用户骑行数据,那么你需要去找单车部门的BI对接数据。

  2、元数据Metastore:元数据是Hive中关于数据的数据。它包含了数据库、表、列、分区、用户权限以及其他与Hive管理的数据相关的信息。这些元数据存储在Metastore中,它可以是嵌入式的Derby数据库,也可以是独立的MySQL数据库。推荐使用MySQL来存储元数据,因为它支持多用户并发访问,且具有更好的可扩展性和稳定性。通过维护这些元数据,Hive能够跟踪数据的结构和位置,从而在执行查询时能够正确地定位和处理数据。

【注意】:Hive会把结构化数据解析为Hive表,那么这些表的数据如果再存放在HDFS,查一下表信息就要等一段时间,就没法管理了。因此是存在DB中,保证用户体验。

  3、Thrift:Thrift是一个跨语言的服务框架,它允许客户端使用不同的编程语言与Hive进行通信。这意味着,无论开发者使用Java、Python、C++还是PHP等语言,他们都可以通过Thrift定义的接口与Hive进行交互。这种跨语言支持极大地提高了Hive的可用性和灵活性,使得它能够被集成到各种不同的应用和服务中。

【注意】:工作中,算法和数仓人员都会用Python,如果你再偏工程点,Java也会要写。因此等你到实际生产开发中就会发现这些工具为什么要跨语言。。。。因为你极有可能今天这个项目是用Python写的,下个项目是用Java写的,下下个项目又跳到C++了。最近感觉学习能力比专业能力更重要,任务完成是目的,而语言只是手段。

  4、驱动器Driver:驱动器是Hive的核心组件之一,负责处理用户提交的查询请求。主要工作是解析HQL,转换为MapReduce(MR)或Spark作业提交。

【注意】:Spark地位等同于MapReduce,但是比MapReduce快很多。最初Hive的执行引擎是MapReduce,后来Spark也兼容了Hive。因此现在写HQL都使用Spark作为执行引擎,不再用MapReduce了。

HQL

  HQL中有一些让我初次接触时让我比较惊艳的设计和概念,所以这里着重介绍一下它比MySQL更惊艳的地方。HQL基本语法和SQL一致,这里不会介绍。

表类型

  在Hive中,根据数据的处理和管理方式,可以将表分为内部表(也称为管理表)和外部表。

  内部表:内部表是Hive中最为常见的一种表类型,由Hive完全管理。当我们在Hive中创建一个内部表时,表的数据实际上被存储在Hive所管理的HDFS上的特定位置。当我们执行删除内部表的命令时,Hive不仅会从其元数据中删除表的记录,而且还会删除在HDFS上与该表关联的所有数据文件。

【注意】:内部表的存储地址是/user/hive/warehouse/your_db_name.db/table_name

  外部表:在Hive中创建外部表时,指定一个指向HDFS上数据文件的外部位置,但Hive并不拥有这些数据。这意味着,当我们删除一个外部表时,Hive仅会从其元数据存储中移除表的元数据信息,而不会删除HDFS上的实际数据文件。

创建表语法

  在用Hive创建表的时候,需要指定一些有趣的分隔符。

  下面是一个创建表的基本例子,展示了如何创建一个内部表:

CREATE TABLE [IF NOT EXISTS] table_name (column1_name '字段注释',column2_name '字段注释',...columnN_name '字段注释'
)
[COMMENT '表注释']
[ROW FORMAT DELIMITED]
[FIELDS TERMINATED BY char]
[STORED AS file_format];

  和MySQL比较不同的是下面三个:

  - ROW FORMAT DELIMITED: 指定表的行格式。这通常用于指定字段之间的分隔符。
  - FIELDS TERMINATED BY char: 指定字段之间的分隔符。
  - STORED AS file_format: 指定表的存储格式。常见的存储格式包括 TEXTFILE, SEQUENCEFILE, ORC, 和 PARQUET

  也就是说,在创建表时,可以指定每个字段之间的分隔符、行之间的分隔符和文件类型。

【注意】:这不就是excel、csv嘛!你可以直接下载下来然后用pandas加载,只是有可能数据量巨大,你的内存会爆。

分区

  分区表实际上就是把一个表在HDFS上的文件建立独立的文件夹,每个文件夹对应表的一个分区;相当于把一个大数据集分割成了许多小数据集,这样做可以把数据管理的很有条理。并且在使用where查询并且指定分区的时候,查询效率也会增加很多。

  创建分区表的语法:

create table(字段名 数据类型,...
)
partitioned by (字段 数据类型)
row format delimited fields terminated by ',';

数据导入导出

  Hive中的数据导入与导出有非常多种写法,并且这些写法在不同的场景下很有用,下面列出具有代表性的几个。

  一、Insert语句把Hive表导出到HDFS

insert overwrite directory
'hdfs://user/opt/module/hive-3.1.2/datas/'
select * from student1;

  二、HIVE Shell命令把Hive表导出到HDFS

 hive -e "select * from db_hive.student1" > 0000.txt

【注意】:Insert语句是在Hive的Cli环境下写的。Hive Shell可以在bash环境里写。

  一、insert导入HDFS文件到Hive表

load data inpath 'hdfs://xxx/xxx/student.txt'
overwrite into table student4;

  二、insert根据HQL查询结果导入到Hive表

insert overwrite table student5
select id,name from student1;

  三、create as 根据查询结果创建

create table if not exists student6
as 
select id,name from student1;

  四、通过location指定表的源数据

create external table if not exists student6(id int,name string
)
row format delimited fields terminated by ','
location '/export/student/data';

【注意】:insert语句分别支持外部文件和查询结果导入,create as 是直接根据查询结果先创建再导入,location是把表关联到一个地址去。写法五花八门,主要还是一看场景、二看怎么做方便工作量小。

函数

  Hive在查询时,除了可以用普通SQL之外,还可以加入函数来处理字段。Hive的函数除了内置函数,还有UDF(用户自定义函数)。UDF非常滴炫酷。

内置函数

  内置函数SQL也有,最简单的有MINMAX这些,Hive里比较高级的内置函数如下:

  collect_list 是一个聚合函数,用于将指定列的所有值收集到一个列表中。当你需要对某一列的所有值进行集合操作时,这个函数非常有用。例如,如果你想要获取一个部门所有员工的姓名列表,可以使用 collect_list 来实现。

SELECT department, collect_list(name) as employee_names
FROM employees
GROUP BY department;

  lateral view 是一个非常有用的操作,它允许你将一个表的列值拆分成多行,并与原始表的行进行连接。这在处理数组或映射类型的列时特别有用。结合 explode 函数,你可以将数组或映射中的每个元素都转换成单独的一行。

SELECT id, name, salary
FROM employees
LATERAL VIEW explode(skills) AS skill;

  explode 是一个UDTF(User-Defined Table-Generating Function,用户定义的表生成函数),它用于将数组或映射类型的单个列拆分成多行。explode 通常与 lateral view 一起使用,以便将数组或映射中的每个元素转换成单独的一行。

SELECT id, skill
FROM employees
LATERAL VIEW explode(skills) AS skill;

  concat 是一个字符串函数,它用于将多个字符串连接成一个单一的字符串。当你需要将多个列的值合并成一个字符串时,concat 函数非常有用。

SELECT concat(first_name, ' ', last_name) as full_name
FROM employees;

  concat_wsconcat 的一个变体,它允许你指定一个分隔符来连接字符串。这在连接列值时提供了更多的灵活性,特别是当你需要在一个特定的分隔符之间插入值时。

SELECT concat_ws('-', first_name, middle_name, last_name) as full_name
FROM employees;

UDF

  UDF允许用户自己定义封装函数,然后调用处理,最常用的就是Java、Python来实现。

Java

  首先,你需要继承Hive提供的类。对于UDF,可以继承 org.apache.hadoop.hive.ql.udf.generic.GenericUDF 类;这个类提供了实现函数的基本框架,包括输入参数的类型检查、执行逻辑的实现等。

  在继承的类中,你需要实现几个抽象方法,这些方法定义了函数的行为。对于UDF,你需要实现 evaluate() 方法。这个方法是函数执行的核心,你需要在这里编写具体的逻辑。

  一旦你的函数实现完成,你需要将它们打包成jar文件,然后将这个jar文件上传到Hive的 lib 目录下。

  在Hive命令窗口中,你可以通过以下命令来创建函数:

# 添加jar包
add jar 自定义jar包的路径;
# 创建Function,temporary表示添加临时的function
create [temporary] function [if not exists] 函数名称 "自定义函数的全类名";
# 删除函数
drop [temporary] function [if exists] 函数名称;

  一旦函数创建成功,你就可以在Hive查询中使用它了。例如,如果你创建了一个名为 my_udf 的UDF,你可以在查询中这样使用:

SELECT my_udf(column1), column2
FROM table;

【注意】:UDF其实有三种:UDF、UDAF、UFTF,分别表示“一对一”、“多对一”、“一对多”。这里只介绍UDF,主要是和Python的写法比较一下。

Python

  Python 实现的 UDF、UDAF、UDTF 函数,需要对输入的一整行的数据进行处理,而并不是针对某一个字段进行处理!

  读取每一行的输入:可以使用 Python 中的标准输入流来读取。需要注意的是,无论 Hive 的表中是以什么样的字符进行分隔的,这里读取到的字段之间始终是以\t进行分隔的!因此我们也必须要使用\t进行字段的切割。

  输出一行的数据:在将一整行的数据处理完成之后,如果需要输出的时候,直接使用 print 函数打印即可。与输入的一样,输出的不同的字段之间也必须要使用\t进行分隔!

  UDAF 函数实现、UDTF 函数实现:如果实现 UDAF、UDTF 这种输入行和输出行不一致的情况,直接控制 print 函数的输出次数即可。一次的 print 就会生成一行的数据,因此合理控制 print 函数的调用次数,即可实现 UDAF、UDTF 函数。

-- 应用UDF
add file example.py-- 处理一列
select transform(t_name) using 'python3 example.py' as (t_name) from example_01;
-- 查询两列
select transform(t_name, t_gender) using 'python3 example.py' as (t_name, t_gender) from example_01;

【注意】:Java的UDF和Python的UDF调用时非常不一样,要牢记。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/53514.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

分布式协调服务--ZooKeeper

文章目录 ZooKeeperzk的由来zk解决了什么问题 ZK工作原理ZK数据模型zk功能1.命名服务2.状态同步3.配置中心4.集群管理 zk部署单机启动zk验证zk zk集群集群角色选举过程1.节点角色状态2.选举ID3.具体过程4.心跳机制5.ZAB协议 ZooKeeper 选举示例1.第一轮投票:2.节点收…

Unity TextMeshPro 设置竖排

默认竖排是这样的 但是我们要的竖排效果并不是这样我们要是竖排连续的根据文本限制来进行换行 第一步我们先设置文本的旋转Z轴为90如下图 然后我们给文本加一个Tag <rotate270> 如下图 但是这个效果还是不是我们想要的效果我们可以使用TexeMeshPro提供的一个选项EnableR…

Python画笔案例-041 绘制正方形阶梯

1、绘制正方形阶梯 通过 python 的turtle 库绘制正方形阶梯&#xff0c;如下图&#xff1a; 2、实现代码 绘制正方形阶梯&#xff0c;以下为实现代码&#xff1a; """正方形阶梯.py """ import turtledef draw_square(length):for _ in range(6…

以太网--TCP/IP协议(一)

概述 以太网是局域网的一种&#xff0c;其他的比如还有令牌环、FDDI。和局域网对应的就是广域网&#xff0c;如Internet&#xff0c;城域网等。 从网络层次看&#xff0c;局域网协议主要偏重于低层&#xff08;业内一般把物理层、数据链路层归为低层&#xff09;。以太网协议…

Qt工程使用MQTT-C库与mqtt服务器数据通信

实现mqtt订阅与发布话题&#xff0c;与mqtt服务器进行数据通信 编译环境&#xff1a;Qt5.15.2 vs2019 需要mqttc库&#xff1a;mqttc.lib, mqttc.dll&#xff08;根据MQTT-C源码编译出来的库&#xff0c;参考cmake编译MQTT-C源码-CSDN博客&#xff09; 一、Qt pro文件编写 …

数据结构C //线性表ADT结构及相关函数

数据结构&#xff08;C语言版&#xff09;严蔚敏 吴伟民 线性表ADT结构及相关函数 环境&#xff1a;Linux Ubuntu&#xff08;云服务器&#xff09; 工具&#xff1a;vim 代码块&#xff08;头文件&#xff0c;函数文件&#xff0c;主文件&#xff09; list.h头文件 /****…

LeetCode 2181.合并零之间的节点

题目描述 给你一个链表的头节点 head &#xff0c;该链表包含由 0 分隔开的一连串整数。链表的 开端 和 末尾 的节点都满足 Node.val 0 。 对于每两个相邻的 0 &#xff0c;请你将它们之间的所有节点合并成一个节点&#xff0c;其值是所有已合并节点的值之和。然后将所有 0 …

浏览器百科:网页存储篇-如何在Chrome中打开IndexedDB窗格(十一)

1.引言 在现代Web开发中&#xff0c;网页存储技术扮演着至关重要的角色。IndexedDB作为一种低级API&#xff0c;允许客户端存储大量结构化数据&#xff0c;并提供高性能的搜索能力。在上一篇文章中&#xff0c;我们深入探讨了IndexedDB的基础知识及其应用场景。为了更有效地调…

安全产品概述

防火墙 防火墙的核心功能是过滤掉有害的流量&#xff0c;在专用网络和公共网络之间建立保护屏障。防火墙过滤通常基于一系列规则&#xff0c;如 IP 地址、域名、协议、端口号、关键字等&#xff0c;对入站和出站的流量进行过滤。这些规则也称为访问控制列表&#xff08;ACCESS…

网络编程day04(UDP、Linux IO 模型)

目录 【1】UDP 1》通信流程 2》函数接口 1> recvfrom 2> sendto 3》代码展示 1> 服务器代码 2> 客户端代码 【2】Linux IO 模型 场景假设一 1》阻塞式IO&#xff1a;最常见、效率低、不耗费CPU 2》 非阻塞 IO&#xff1a;轮询、耗费CPU&#xff0c;可以处…

Spring Boot属性注入的多种方式!

Spring Boot的一个问题&#xff0c;证明你是不是真正的 "会用" Spring boot ?Spring Boot的一个问题&#xff0c;直接暴露你是不是真正使用Spring Boothttps://mp.weixin.qq.com/s?__bizMzkzMTY0Mjc0Ng&mid2247484040&idx1&sn64ad15d95e44c874cc890973…

2024年CCPC网络赛A题题解 —— 军训Ⅰ(gym105336A)

个人认为很唐的一道题&#xff0c;考虑到不少人可能懒得写&#xff0c;我这里给大家发个代码叭&#xff0c;还有一点点题解&#xff08;因为真的不是很难&#xff09;。这是题面&#xff1a; 然后我来讲讲怎么做&#xff0c;不觉得会有多少人题目意思都理解不了叭&#xff1f;这…

码上进阶_刷题模块测试_用例设计

码上进阶_刷题模块测试_用例设计 系统概述&#xff1a; 码上进阶是为程序员专门打造的交流平台&#xff0c;采用主流的微服务框架和C端技术栈作为技术基础。在这个平台上&#xff0c;程序员 可以通过刷题、练习和模拟面试来提升自己的面试能力。 功能测试&#xff1a; 登录…

Linux 常用命令 - tail 【显示文件最后几行内容】

简介 tail 这个命令源自英文单词 “尾巴”&#xff0c;它的主要功能是显示文件的最后几行内容。通过使用 tail&#xff0c;用户可以查看文件的最新添加内容&#xff0c;特别是对于监控日志文件来说非常有用。tail 命令默认显示文件的最后 10 行&#xff0c;但这可以通过参数调…

数学建模_数据预处理流程(全)

数据预处理整体流程图 一般数据预处理流程 处理缺失值&#xff1a;填补或删除缺失值。处理异常值&#xff1a;检测并处理异常值。数据编码&#xff1a;将分类变量进行标签编码或独热编码。数据标准化/归一化&#xff1a;对数据进行标准化或归一化处理。连续变量离散化&#xff…

基于JAVA+SpringBoot+Vue的企业级工位管理系统

基于JAVASpringBootVue的企业级工位管理系统 前言 ✌全网粉丝20W,csdn特邀作者、博客专家、CSDN[新星计划]导师、java领域优质创作者,博客之星、掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java技术领域和毕业项目实战✌ &#x1f345;文末附源码下载链接&#x1f345; …

WinCC 中对 VBS 进行单步执行调试

以前应该写过文章给各位展示如何在WinCC 中通过自身控件对脚本&#xff08;C、VBS&#xff09;进行脚本诊断和排错。但是也有用户反馈说在编写了一些相对复杂的脚本后&#xff0c;WinCC自身控件无法做到单步调试&#xff0c;也会影响脚本的诊断调试效率。如果能够对WinCC 中的脚…

论文解读:《LAMM: Label Alignment for Multi-Modal Prompt Learning》

系列文章目录 文章目录 系列文章目录LAMM: Label Alignment for Multi-Modal Prompt Learning学习1、论文细节理解1、研究背景2、论文贡献3、方法框架4、研究思路5、实验6、限制 LAMM: Label Alignment for Multi-Modal Prompt Learning学习 1、论文细节理解 VL模型和下游任务…

Linux_kernel驱动开发11

一、改回nfs方式挂载根文件系统 在产品将要上线之前&#xff0c;需要制作不同类型格式的根文件系统 在产品研发阶段&#xff0c;我们还是需要使用nfs的方式挂载根文件系统 优点&#xff1a;可以直接在上位机中修改文件系统内容&#xff0c;延长EMMC的寿命 【1】重启上位机nfs服…

Docker初识(Docker技术集群与应用)

一、基础设施即服务 IaaS&#xff08;Infrastructure as a Service&#xff09; eg&#xff1a;购买的云服务器&#xff0c;就是IaaS 提供给客户的服务是对所有设施的利用&#xff0c;包括处理、存储、网络和其他基本的计算资源。客户能够部署和运行任意软件&#xff0c;包括…