SparkSQL入门

1、SparkSQL是什么?

结论:SparkSQL 是一个即支持 SQL 又支持命令式数据处理的工具

2、SparkSQL 的适用场景?

结论:SparkSQL 适用于处理结构化数据 的场景,而SparkRDD 主要用于处理 非结构化数据半结构化数据

2.1 结构化、非结构化、半结构化数据的区别

(1)结构化数据: 一般指数据有固定的 Schema(数据具体的结构信息, 例如在用户表中, name 字段是 String 型, 那么每一条数据的 name 字段值都可以当作 String 来使用

(2)半结构化数据: 一般指的是数据没有固定的 Schema, 但是数据本身是有结构的

解释:

没有固定Schema:指的是半结构化数据是没有固定的 Schema 的, 可以理解为没有显式指定 Schema。

举例:比如说一个用户信息的 JSON 文件, 第一条数据的 phone_num 有可能是 String, 第二条数据虽说应该也是 String, 但是如果硬要指定为 BigInt, 也是有可能的

因为没有指定 Schema, 没有显式的强制的约束

有结构:虽说半结构化数据是没有显式指定 Schema 的, 也没有约束, 但是半结构化数据本身是有有隐式的结构的, 也就是数据自身可以描述自身。

举例:

例如 JSON 文件, 其中的某一条数据是有字段这个概念的, 每个字段也有类型的概念, 所以说 JSON 是可以描述自身的, 也就是数据本身携带有元信息

Scala 复制代码
{
     "firstName": "John",
     "lastName": "Smith",
     "age": 25,
     "phoneNumber":
     [
         {
           "type": "home",
           "number": "212 555-1234"
         },
         {
           "type": "fax",
           "number": "646 555-4567"
         }
     ]
 }

总结:

3、程序入口SparkSession

SparkSession

3.1 SparkContext 作为 RDD 的创建者和入口, 其主要作用有如下两点:

  • 创建 RDD, 主要是通过读取文件创建 RDD

  • 监控和调度任务, 包含了一系列组件, 例如 DAGScheduler, TaskSheduler

3.2 为什么无法使用 SparkContext 作为 SparkSQL 的入口?

(1)SparkContext 在读取文件的时候, 是不包含 Schema 信息的, 因为读取出来的是 RDD

(2)SparkContext 在整合数据源如 Cassandra, JSON, Parquet 等的时候是不灵活的, 而 DataFrame 和 Dataset 一开始的设计目标就是要支持更多的数据源

(3)SparkContext 的调度方式是直接调度 RDD, 但是一般情况下针对结构化数据的访问, 会先通过优化器优化一下

所以 SparkContext 确实已经不适合作为 SparkSQL 的入口, 所以刚开始的时候 Spark 团队为 SparkSQL 设计了两个入口点, 一个是 SQLContext 对应 Spark 标准的 SQL 执行, 另外一个是 HiveContext 对应 HiveSQL 的执行和 Hive 的支持.

在 Spark 2.0 的时候, 为了解决入口点不统一的问题, 创建了一个新的入口点 SparkSession, 作为整个 Spark 生态工具的统一入口点, 包括了 SQLContext, HiveContext, SparkContext 等组件的功能

3.3 新的入口应该有什么特性?

  • 能够整合 SQLContext, HiveContext, SparkContext, StreamingContext 等不同的入口点

  • 为了支持更多的数据源, 应该完善读取和写入体系

  • 同时对于原来的入口点也不能放弃, 要向下兼容

4、DataFrame

与RDD类似,DataFrame也是一个分布式数据容器。然而DataFrame更像传统数据库的二维表 格,除了数据以外,还掌握数据的结构信息,即schema。一般情况下要先通过 DataFrame 或者 Dataset 注册一张临时表, 然后使用 SQL 操作这张临时表。

SparkSQL 对外提供的 API 有两类, 一类是直接执行 SQL, 另外一类就是命令式. SparkSQL 提供的命令式 API 就是DataFrame DSL(Domain Specific Language)API(也称为 Dataset API), 暂时也可以认为 DataFrame 就是 Dataset, 只是在不同的 API 中返回的是 Dataset 的不同表现形式。

版本演变:

  • DataFrame:在Spark 1.3及之后的版本中引入,是一个分布式的数据集合。它可以被看作是一个表格型的数据结构,包含了一组有序的列,每列可以是不同的值类型(数值、字符串、布尔型值等)。DataFrame既有行索引也有列索引,可以看作是由Series组成的字典(共同使用一个索引)。
  • Dataset:在Spark 1.6及之后的版本中引入,是DataFrame的扩展。Dataset是一个强类型、不可变的分布式数据集合,它提供了编译时类型安全检查。Dataset是Spark SQL中一个新的分布式数据集合抽象,提供了RDD的优势(强类型、使用强大的lambda函数的能力)以及Spark SQL优化执行引擎的优点。
  • 在Spark 2.0及之后的版本中,DataFrame和Dataset的API已经统一,DataFrame被看作是Dataset[Row]的一个特例,即具有schema的分布式Row对象的集合。

5、入门程序案例(直接执行 SQL方式)

统计班级人数

Scala 复制代码
import org.apache.spark.sql.{DataFrame, Dataset, Row, SaveMode, SparkSession}


object Demo1WorldCount {
  def main(args: Array[String]): Unit = {
    /**
     * 在新版本的Scala中,如果想要编写spark sql,需要使用新的spqrk入口类:Sparksession
     *
     */
    val sparkSession: SparkSession = SparkSession.builder()
      .master("local")
      .appName("wc spark sql")
      .getOrCreate()

    /**
     * spark sql和spark core的核心数据类型不一样
     * 1、读取数据构建一个DataFrame,相当于一张表
     */
    //1500100954,咸芷天,21,女,文科二班
    val studentsDF: DataFrame = sparkSession.read
      .format("csv") //指定读取文件的格式
      .schema("id String,name String,age String,gender String,clazz String") //指定列的名称及类型,多个列之间用逗号分割
      .option("sep", ",") //指定分割符,csv格式读取默认是英文逗号
      .load("spark/data/student.csv") //指定读取文件98的位置,可以使用相对路径

    //    studentsDF.show() //查看DF中的数据内容(表内容)
    //    studentsDF.printSchema()   //查看studentsDF表结构

    /**
     * DF本身是无法直接写sql的,需要将DF注册为一个视图,才可以写sql语句
     */
    studentsDF.createOrReplaceTempView("students") //起一个表名,给后面的sql语句使用

    /**
     * 3、可以编写sql语句(统计班级人数)
     * 注意:spark完全兼容hive sql
     */
//    val resDF: DataFrame = sparkSession.sql("select * from students")  //如果语句短,可以写在一行,使用""即可
    val resDF: DataFrame = sparkSession.sql(
      """
        |select
        |clazz,
        |count(1) as clazz_number
        |from students
        |group by clazz
        |""".stripMargin)              //当语句过长可以使用""""""三引号



    /**
     * 4、将计算的结果DF保存到hdfs中
     */
    val resDS: Dataset[Row] = resDF.repartition(1)   //设置分区数
    resDS.write
      .format("csv") //指定输出文件的格式
      .option("sep",",")   //指定分隔符
      .mode(SaveMode.Append)    //使用SaveMode枚举类,设置为覆盖写
      .save("hdfs://master:9000/bigdata29/spark/clazz_number")    //指定hdfs输出的文件路径

  }
}

参考原文链接:https://blog.csdn.net/qq_26442553/article/details/114970346

相关推荐
码上淘金15 分钟前
Apache Flink架构深度解析:任务调度、算子数据同步与TaskSlot资源管理机制
大数据·架构·flink
fruge33 分钟前
git上传 项目 把node_modules也上传至仓库了,在文件.gitignore 中忽略node_modules 依然不行
大数据·git·elasticsearch
python资深爱好者1 小时前
什么容错性以及Spark Streaming如何保证容错性
大数据·分布式·spark
B站计算机毕业设计超人2 小时前
计算机毕业设计hadoop+spark旅游景点推荐 旅游推荐系统 旅游可视化 旅游爬虫 景区客流量预测 旅游大数据 大数据毕业设计
大数据·hadoop·爬虫·深度学习·机器学习·数据可视化·推荐算法
qiquandongkh3 小时前
2025年股指期货和股指期权合约交割的通知!
大数据·金融·区块链
Ray.19984 小时前
优化 Flink 消费 Kafka 数据的速度:实战指南
大数据·flink·kafka
猪猪果泡酒4 小时前
spark
spark
D愿你归来仍是少年4 小时前
Python解析 Flink Job 依赖的checkpoint 路径
大数据·python·flink
说私域5 小时前
利用开源AI智能名片2+1链动模式S2B2C商城小程序构建企业私域流量池的策略与实践
大数据·人工智能·小程序·开源
yinbp5 小时前
bboss v7.3.5来袭!新增异地灾备机制和Kerberos认证机制,助力企业数据安全
大数据·elasticsearch·微服务·etl·restclient·bboss