详解 Spark SQL 核心编程知识

一、SparkSQL 概述

1. 概念

Spark SQL 是 Spark 用于结构化数据 (structured data) 处理的 Spark 模块,使用 SQL 的方式简化 RDD 的开发

2. Hive VS SparkSQL

  • Hive 是早期唯一运行在 Hadoop 上的 SQL-on-Hadoop 工具,但是 MapReduce 计算过程中大量的中间磁盘落地过程消耗了大量的 I/O,降低的运行效率
  • Shark 是为了提高 SQL-on-Hadoop的效率而产生的 SQL-on-Hadoop 工具,是基于 Hive 所开发的,它修
    改了 Hive 中的内存管理、物理计划和执行三个模块,并使之能运行在 Spark 引擎上
  • 由于 Shark 对于 Hive 存在太多依赖(如采用 Hive 的语法解析器、查询优化器等等),制约了其发展,SparkSQL 由此应运而生,它抛弃了原有 Shark 的代码,但汲取了 Shark 的一些优点,如内存列存储(In-Memory Columnar Storage)、 Hive 兼容性等
    • 数据兼容方面 SparkSQL 不但兼容 Hive,还可以从 RDD、parquet 文件、JSON 文件中获取数据,未来版本甚至支持获取 RDBMS 数据以及 cassandra 等 NOSQL 数据
    • 性能优化方面 除了采取 In-Memory Columnar Storage、byte-code generation 等优化技术外、将会引进 Cost Model 对查询进行动态评估、获取最佳物理计划等等
    • 组件扩展方面 无论是 SQL 的语法解析器、分析器还是优化器都可以重新定义,进行扩展
  • Shark 停止开发后,发展出了两个支线,其中 SparkSQL 作为 Spark 生态的一员继续发展,而不再受限于 Hive,只是兼容 Hive;而 Hive on Spark 是一个 Hive 的发展计划,该计划将 Spark 作为 Hive 的底层引擎之一,由此 Hive 将不再受限于一个引擎,可以采用 Map-Reduce、Tez、Spark 等引擎

3. SparkSQL 特点

  • 易整合:无缝的整合了 SQL 查询和 Spark 编程
  • 统一的数据访问:使用相同的方式连接不同的数据源
  • 兼容 Hive:在已有的仓库上直接运行 SQL 或者 HiveQL
  • 标准数据连接:通过 JDBC 或者 ODBC 来连接

4. 两大数据模型

  • DataFrame:一种以 RDD 为基础的分布式数据集,类似于传统数据库中的二维表格
  • DataSet:是 Spark 1.6 中添加的一个新抽象,是 DataFrame 的一个扩展

二、SparkSQL 核心编程

1. 上下文对象

  • SparkCore 中执行应用程序前构建的上下文环境对象为 SparkContext
  • SparkSQL 中执行应用程序前构建的上下文环境对象为:
    • 老版本:SQLContext,用于 Spark 自己提供的 SQL 查询;HiveContext,用于连接 Hive 的查询
    • 新版本:SparkSession,实质上是 SQLContext 和 HiveContext 的组合,内部封装了 SparkContext

2. DataFrame

2.1 介绍
  • DataFrame 是一种以 RDD 为基础的分布式数据集,类似于传统数据库中的二维表格。与 RDD 的主要区别在于,DataFrame 带有 schema 元信息,即 DataFrame 所表示的二维表数据集的每一列都带有名称和类型
  • 与 Hive 类似,DataFrame 也支持嵌套数据类型(struct、array 和 map)
  • DataFrame 是为数据提供了 Schema 的视图,可以把它当做数据库中的一张表来看待
  • DataFrame 是懒执行的,但性能上比 RDD 要高,主要原因:优化的执行计划,即查询计划通过 Spark catalyst optimiser 进行优化
2.2 创建
2.2.1 从 Spark 数据源创建
/**基本语法:SparkSession.read.[data_format]可用的数据源格式:csv format jdbc json load option options orc parquet schema table text textFile
*/
// 从一个 json 文件中创建 DataFrame
val df = sparkSession.read.json("data/user.json")// 展示 DataFrame 数据
df.show()
2.2.2 从 RDD 创建
/**基本语法:RDD.toDF(col1, col2, ...)注意:1.必须先创建 SparkSession 对象,使用 val 修饰且命名为 spark2.引入:import spark.implicits._  (此处的 spark 为 SparkSession 对象)
*/
val rdd = sc.makeRDD(List(1,2,3,4))
val df = rdd.toDF("id")
df.show()//使用样例类
case class User(val name: String, val age: Int)val rdd1 = sc.makeRDD(List(("tom", 18), ("jerry", 17)
)).map(t => User(t._1, t._2))rdd1.toDF.show// DataFrame 转换为 RDD
val rdd2: RDD[org.apache.spark.sql.Row] = df.rdd
2.2.3 从 Hive Table 创建
/**基本语法:SparkSession.sql("select * from hive_table")*/
val df = sparkSession.sql("select * from user")
df.show()
2.3 SQL 语法
// 1.创建临时视图
// 1.1 session 范围有效
df.createTempView("user")
df.createOrReplaceTempView("user")// 1.2 应用范围有效
df.createGlobalTempView("emp")
df.createOrReplaceGlobalTempView("emp")// 2.使用 SQL 语法查询视图
sparkSession.sql("select * from user").show()
// 访问全局视图需要加上 global_temp 前缀
sparkSession.newSession().sql("select * from global_temp.emp").show()
2.4 DSL 语法

domain-specific language,可以直接在 DataFrame 中管理结构化的数据

// 1.查看 DataFrame 的 Schema 信息
df.printSchema()// 2.查看某列数据
df.select("username").show()
// 2.1 查看某列计算后的数据:涉及到运算的时候,每列都必须使用 $ 或者单引号表达式
// 注意:必须先创建 SparkSession 对象,使用 val 修饰且命名为 spark,然后 import spark.implicits._
df.select($"age" + 1).show()
df.select($"username", $"age" + 1).show()
df.select('username, 'age + 1).show()// 3.按条件查询数据
df.filter('age > 20).show()// 4.分组计数
df.groupBy("age").count().show()

3. DataSet

3.1 介绍
  • DataSet 是具有强类型的数据集合,需要提供对应的类型信息,比如 DataSet[Car],DataSet[Person]
  • DataSet 是 DataFrame API 的一个扩展,是 SparkSQL 最新的数据抽象
  • 用户友好的 API 风格,既具有类型安全检查也具有 DataFrame 的查询优化特性
  • 用样例类来对 DataSet 中定义数据的结构信息,样例类中每个属性的名称直接映射到 DataSet 中的字段名称
  • DataFrame 是 DataSet 的特列,DataFrame = DataSet[Row] ,所以可以通过 as 方法将 DataFrame 转换为 DataSet。Row 是一个类型,跟 Car、Person 这些的类型一样,所有的表结构信息都用 Row 来表示。获取数据时需要指定顺序
3.2 创建
3.2.1 从序列创建
/**基本语法:List/Seq.toDS()
*/
// 1.基本类型序列创建
val list = List(1,2,3,4)
val ds = list.toDS()
ds.show()// 2.样例类序列创建
case class Person(name: String, age: Int)
val list1 = List(Person("tom", 20), Person("jerry", 18))
val ds1 = list1.toDS()
ds1.show()
3.2.2 从 RDD 创建
/**基本语法:RDD.toDS(),最好使用样例类类型的 RDDDataSet 转成 RDD:DataSet.rdd()
*/
case class Person(name: String, age: Int)val rdd = sc.makeRDD(Person("tom", 20), Person("jerry", 18))val ds = rdd.toDS()
ds.show()val rdd1 = ds.rdd()
3.2.3 从 DataFrame 创建
/**基本语法:DataFrame.as[Class]DataSet 转成 DataFrame:DataSet.toDF
*/
val df = sc.makeRDD(List(("tom", 20), ("jerry", 18)
)).toDF("name", "age")df.show()// 定义样例类型
case class Person(name: String, age: Int)val ds = df.as[Person]
ds.show()val df1 = ds.toDF()
df1.show()

4. RDD/DataFrame/DataSet 的关系

在这里插入图片描述

  • RDD 产生于 Spark1.0 版本,DataFrame 产生于 Spark1.3 版本,Dataset 产生于 Spark1.6 版本
  • 三者都是 Spark 平台下的分布式弹性数据集,为处理超大型数据提供便利,都有惰性机制,都会根据 Spark 的内存情况自动缓存运算,都有 partition 的概念
  • RDD 不支持 SparkSQL 操作,而 DataFrame 与 DataSet 均支持 SparkSQL 的操作;DataFrame 其实是 DataSet 的一个特例

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

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

相关文章

URL路由基础

本书1-7章样章及配套资源下载链接: https://pan.baidu.com/s/1OGmhHxEMf2ZdozkUnDkAkA?pwdnanc 源码、PPT课件、教学视频等,可以从前言给出的下载信息下载,大家可以评估一下。 对于高质量的Web应用来讲,使用简洁、优雅的URL设计模式非常…

时间序列的谱分解

refer:15.pdf (berkeley.edu) Stat 153 Fall 2010 (berkeley.edu)

linux mtd分区应用操作sample之某分区擦除

什么是擦除? 把flash相关的区域数据bit置为1的过程 #include <mtd/mtd-user.h> #include <mtd/mtd-abi.h> struct erase_info_user {__u32 start; // 起点 __u32 length; //长度 块大小对齐 不然报参数失败 };struct erase_info_user64 {__u64 sta…

Linux 驱动设备匹配过程

一、Linux 驱动-总线-设备模型 1、驱动分层 Linux内核需要兼容多个平台&#xff0c;不同平台的寄存器设计不同导致操作方法不同&#xff0c;故内核提出分层思想&#xff0c;抽象出与硬件无关的软件层作为核心层来管理下层驱动&#xff0c;各厂商根据自己的硬件编写驱动…

【逻辑回归】Logistic Regression逻辑回归模型学习笔记

文章目录 序言1. 线性回归2. 逻辑回归2.1 引入逻辑回归的原因2.2 逻辑回归2.3 逻辑回归的应用 3. 逻辑函数3.1 sigmoid函数3.2 sigmoid函数的性质3.3 决策边界3.4 对数几率 4. 损失函数4.1 为什么说逻辑回归时概率类模型4.2 为什么要进行极大似然估计4.3 利用MLE如何推导出损失…

Linux下的配置工具menuconfig+配置文件(Kconfig/.config/defconfig)

我们都知道,嵌入式开发中,或者说C语言中,配置基本都是通过宏定义来决定的,在MCU开发中,代码量比较小,配置项也比较少,我们直接修改对应的宏定义即可。 但是,Linux开发中,操作系统、驱动部分还有应用部分加起来,代码量极大,配置项目也非常多,这时候,就需要对这些配…

HackTheBox-Machines--Cronos

文章目录 0x01 信息收集0x02 命令注入漏洞0x03 权限提升 Cronos 测试过程 0x01 信息收集 1.端口扫描 发现 SSH&#xff08;22&#xff09;、DNS&#xff08;53&#xff09;、HTTP&#xff08;80&#xff09;端口 nmap -sC -sV 10.129.227.2112.53端口开启&#xff0c;进行DNS…

【LeetCode刷题】前缀和解决问题:742.寻找数组的中心下标、238.除自身以外数组的乘积

【LeetCode刷题】Day 15 题目1&#xff1a;742.寻找数组的中心下标思路分析&#xff1a;思路1&#xff1a;前缀和思想 题目2&#xff1a;238.除自身以外数组的乘积思路分析思路1&#xff1a;前缀和思想 题目1&#xff1a;742.寻找数组的中心下标 思路分析&#xff1a; 其实题干…

【软件开发规范篇】前言

作者介绍&#xff1a;本人笔名姑苏老陈&#xff0c;从事JAVA开发工作十多年了&#xff0c;带过大学刚毕业的实习生&#xff0c;也带过技术团队。最近有个朋友的表弟&#xff0c;马上要大学毕业了&#xff0c;想从事JAVA开发工作&#xff0c;但不知道从何处入手。于是&#xff0…

Linux——多线程(三)

在上一篇博客中我们讲到了在加锁过程中&#xff0c;线程竞争锁是自由竞争的&#xff0c;竞争能力强的线程会导致其他线程抢不到锁&#xff0c;访问不了临界资源导致其他线程一直阻塞&#xff0c;造成其它线程的饥饿问题&#xff0c;想要解决此问题又涉及一个新概念线程同步 一…

18 EEPROM读写

EEPROM 简介 EEPROM (Electrically Erasable Progammable Read Only Memory&#xff0c;E2PROM)即电可擦除可编程只读存储器&#xff0c;是一种常用的非易失性存储器&#xff08;掉电数据不丢失&#xff09;&#xff0c;EEPROM 有多种类型的产品&#xff0c;此次实验使用的是A…

32位与64位程序下函数调用的异同——计科学习中缺失的内容

前言 今天&#xff0c;通过一个有趣的案例&#xff0c;从反编译的角度看一下C语言中函数参数是如何传递的。 创建main.c文件&#xff0c;将下面实验代码拷贝到main.c文件中。 # main.c #include <stdio.h>int test(int a, int b, int c, int d, int e, int f, int g, …

Docker最新超详细版教程通俗易懂

文章目录 一、Docker 概述1. Docker 为什么出现2. Docker 的历史3. Docker 能做什么 二、Docker 安装1. Docker 的基本组成2. 安装 Docker3. 阿里云镜像加速4. 回顾 hello-world 流程5. 底层原理 三、Docker 的常用命令1. 帮助命令2. 镜像命令dokcer imagesdocker searchdocker…

解锁数据宝藏:高效查找算法揭秘

代码下载链接&#xff1a;https://gitee.com/flying-wolf-loves-learning/data-structure.git 目录 一、查找的原理 1.1 查找概念 1.2 查找方法 1.3平均查找长度 1.4顺序表的查找 1.5 顺序表的查找算法及分析 1.6 折半查找算法及分析 1.7 分块查找算法及分析 1.8 总结…

pytorch学习笔记5

transform 本质上作用是将图片通过transform这个这个工具箱获取想要的结果 tensor就是一个包含神经网络需要的一些理论基础的参数 from torch.utils.tensorboard import SummaryWriter from torchvision import transforms from PIL import Image #tensor数据类型 #通过tra…

1985-2020 年阿拉斯加和育空地区按植物功能类型划分的模型表层覆盖率

ABoVE: Modeled Top Cover by Plant Functional Type over Alaska and Yukon, 1985-2020 1985-2020 年阿拉斯加和育空地区按植物功能类型划分的模型表层覆盖率 简介 文件修订日期&#xff1a;2022-05-31 数据集版本: 1.1 本数据集包含阿拉斯加和育空地区北极和北方地区按…

DPDK基础组件二(igb_uio、kni、rcu)

The Linux driver implementer’s API guide — The Linux Kernel documentation 一、igb_uid驱动 参考博客:https://zhuanlan.zhihu.com/p/543217445 UIO(Userspace I/O)是运行在用户空间的I/O技术 代码位置:dpdk----/kernel/linux/igb_uio目录 igb_uio 是 dpdk 内部实…

学习数据分析思维的共鸣

在这篇文章中&#xff0c;我将分享自己在成长过程中对数据分析思维的领悟&#xff0c;从《数据分析思维-产品经理的成长笔记》这本书引发的共鸣&#xff0c;到数据分析在不同岗位的广泛应用&#xff0c;再到如何将学习与快乐联系起来&#xff0c;以及沟通在数据分析中的重要性。…

cocos入门4:项目目录结构

Cocos Creator 项目结构教程 Cocos Creator 是一个功能强大的游戏开发工具&#xff0c;它为开发者提供了直观易用的界面和强大的功能来快速创建游戏。在使用 Cocos Creator 开发游戏时&#xff0c;合理地组织项目结构对于项目的可维护性和扩展性至关重要。以下是一个关于如何设…

设计模式(十)结构型模式---享元模式(flyweight)

文章目录 享元模式简介结构UML图具体实现UML图代码实现 享元模式简介 享元模式&#xff08;fly weight pattern&#xff09;主要是通过共享对象来减少系统中对象的数量&#xff0c;其本质就是缓存共享对象&#xff0c;降低内存消耗。享元模式将需要重复使用的对象分为两个状态…