Spark SQL是Spark框架的重要组成部分, 主要用于结构化数据处理和对Spark数据执行类SQL的查询。

DataFrame是一个分布式的,按照命名列的形式组织的数据集合。 一张SQL数据表可以映射为一个DataFrame对象,DataFrame是Spark SQL中的主要数据结构。

SqlContext实例是DataFrame和Spark SQL的操作入口, pyspark交互环境中已初始化了一个sqlContext实例, 在提交任务脚本时需要使用一个SparkContext来初始化:

from pyspark.sql import SQLContext
sqlContext = SqlContext(sparkContext)

本文测试环境为Spark 2.1.0, Python API.

创建DataFrame

SqlContext.createDataFrame方法可以从python的list中创建DataFrame:

>>> data = [('a', 1, 18), ('b', 2, 22), ('c', 3, 20)]
>>> df = sqlContext.createDataFrame(data)
>>> df.collect()
[Row(_1=u'a', _2=1, _3=18),
Row(_1=u'b', _2=2, _3=22),
Row(_1=u'c', _2=3, _3=20)]

list中的每一项成为DataFrame中的一行, 每一列的名字默认为_1, _2, _3.

同样可以使用RDD来创建:

>>> data = [('a', 1, 18), ('b', 2, 22), ('c', 3, 20)]
>>> rdd = sc.parallelize(data)
>>> df = sqlContext.createDataFrame(rdd)
>>> df.collect()
[Row(_1=u'a', _2=1, _3=18),
Row(_1=u'b', _2=2, _3=22),
Row(_1=u'c', _2=3, _3=20)]

或者采用更简单的方法:

>>> df = rdd.toDF()
>>> >>> df.collect()
[Row(_1=u'a', _2=1, _3=18),
Row(_1=u'b', _2=2, _3=22),
Row(_1=u'c', _2=3, _3=20)]

createFrame的第二个参数为可选参数schema用于定义每一列的名称和类型:

>>> data = [('a', 1, 18), ('b', 2, 22), ('c', 3, 20)]
>>> df = sqlContext.createDataFrame(data, ['name', 'id', 'age'])
>>> df.collect()
[Row(name=u'a', id=1, age=18),
Row(name=u'b', id=2, age=22),
Row(name=u'c', id=3, age=20)]

同样可以使用元素为dict的列表创建DataFrame实例:

>>> data = [
... {'name':'a', 'id':1, 'age': 18},
... {'name':'b', 'id':2, 'age': 22},
... {'name':'c', 'id':3, 'age': 20}]
>>> df = sqlContext.createDataFrame(data)
>>> df.collect()
[Row(name=u'a', id=1, age=18),
Row(name=u'b', id=2, age=22),
Row(name=u'c', id=3, age=20)]

不过Spark官方推荐使用Row对象来代替dict:

>>> from pyspark.sql import Row
>>> User = Row('name', 'id', 'age')
>>> row1 = User('a', 1, 18)
>>> row2 = User('b', 2, 22)
>>> row3 = User('b', 3, 20)
>>> data = [row1, row2, row3]
>>> df = sqlContext.createDataFrame(data)
>>> df.collect()
[Row(name=u'a', id=1, age=18),
Row(name=u'b', id=2, age=22),
Row(name=u'c', id=3, age=20)]

schema参数也可以使用pyspark中定义的字段类型:

>>> from pyspark.sql.types import StructType, StructField
>>> from pyspark.sql.types import StringType, IntegerType
>>> schema = StructType([
... StructField("name", StringType(), True), # name, type, nullable
... StructField("id", IntegerType(), True),
... StructField("age", IntegerType(), True)])
>>> data = [('a', 1, 18), ('b', 2, 22), ('c', 3, 20)]
>>> df = sqlContext.createDataFrame(data, schema)
>>> df.collect()
[Row(name=u'a', id=1, age=18),
Row(name=u'b', id=2, age=22),
Row(name=u'c', id=3, age=20)]

更多关于createDataFrame方法的信息可以参考官方文档

SqlContext.read是一个pyspark.sql.DataFrameReader对象, 它可以用于根据外部数据源创建DataFrame, 包括读取文件和使用jdbc读取数据库。

详情可以参考官方文档

DataFrame操作

DataFrame提供了一些常用操作的实现, 可以使用这些接口查看或修改DataFrame:

  • df.collect(): 以Row列表的方式显示df中的所有数据
  • df.show(): 以可视化表格的方式打印df中的所有数据
  • df.count(): 显示df中数据的行数
  • df.describe() 返回一个新的DataFrame对象包含对df中数值列的统计数据
  • df.cache(): 以MEMORY_ONLY_SER方式进行持久化
  • df.persist(level): 以指定的方式进行持久化
  • df.unpersist(): 删除缓存

DataFrame的一些属性可以用于查看它的结构信息:

  • df.columns: 返回各列名称的列表

  • df.schema: 以StructType对象的形式返回df的表结构

  • df.dtypes: 以列表的形式返回每列的名称和类型。

    [('name', 'string'), ('id', 'int')]

  • df.rdd 将DataFrame对象转换为rdd

DataFrame支持使用Map和Reduce操作:

  • df.map(func): 等同于df.rdd.map(func)

  • df.reduce(func): 等同于 df.rdd.reduce(func)

DataFrame的结构可以进行一些修改:

  • df.drop(col): 返回一个删除指定列后的DataFrame对象:
>>> df.drop('age')
DataFrame[age:int, id: int]
>>>df.drop(df.name)
DataFrame[age:int, id: int]

同样可以查询DataFrame中特定的记录:

  • df.take(index): 以列表的形式返回df的前n条记录, 下标从1开始

  • df.first(): 返回df中的第一个Row对象

  • df.filter(cond): 返回只包含满足条件记录的新DataFrame对象

>>> df.filter(df.age>=20).collect()
[Row(name=u'b', id=2, age=22), Row(name=u'c', id=3, age=20)]
  • df.select(col): 返回只包含指定列的新DataFrame对象:
>>> df.select('*').collect()
[Row(name=u'a', id=1, age=18), Row(name=u'b', id=2, age=22), Row(name=u'c', id=3, age=20)] >>> df.select(df.id, df.age-1).collect()
[Row(id=1, (age - 1)=17), Row(id=2, (age - 1)=21), Row(id=3, (age - 1)=19)]
  • df.join(other, on=None, how=None)将df和other两个DataFrame对象连接为一个DataFrame对象.

    • on: 指定连接的列
    • how: 指定连接方式:'inner', 'outer', 'left_outer', 'right_outer', 'leftsemi', 默认为'inner'
>>> df.collect()
[Row(name=u'a', id=1, age=18), Row(name=u'b', id=2, age=22), Row(name=u'c', id=3, age=20)]
>>> df2.collect()
[Row(id=1, nation=u'cn'), Row(id=2, nation=u'us'), Row(id=4, nation=u'uk')] >>> df.join(df2, 'id').collect()
[Row(id=1, name=u'a', age=18, nation=u'cn'), Row(id=2, name=u'b', age=22, nation=u'us')]
  • df.limit(num): 返回一个新的DataFrame对象, 其记录数不超过num, 多余的记录将被删除.

  • df.distinct() : 返回一个新的去除重复行后的DataFrame对象

更多信息可以参考官方文档

Spark SQL结构化数据处理的更多相关文章

  1. spark结构化数据处理:Spark SQL、DataFrame和Dataset

    本文讲解Spark的结构化数据处理,主要包括:Spark SQL.DataFrame.Dataset以及Spark SQL服务等相关内容.本文主要讲解Spark 1.6.x的结构化数据处理相关东东,但 ...

  2. SQL 结构化查询语言

    SQL 结构化查询语言 一.数据库的必要性: >>作用:存储数据.检索数据.生成新的数据 1)可以有效结构化存储大量的数据信息,方便用户进行有效的检索和访问. 2)可以有效地保持数据信息的 ...

  3. SQL结构化查询语句

    SQL结构化查询语句 SQL定义了查询所有关系型数据库的规则. 1.通用语法 SQL语句可以单行或者多行书写,以分号结尾 可以使用空格和缩进增强可读性 不区分大小写,但是关键字建议大写 3种注释 注释 ...

  4. SQL结构化查询语言

    一.SQL 结构化查询语言 1.T-SQL 和 SQL的关系 T-SQL是SQL的增强版 2.SQL的组成 2.1 DML (数据操作语言) 增加,修改,删除等数据操作 2.2 DCL (数据控制语言 ...

  5. Spark读取结构化数据

    读取结构化数据 Spark可以从本地CSV,HDFS以及Hive读取结构化数据,直接解析为DataFrame,进行后续分析. 读取本地CSV 需要指定一些选项,比如留header,比如指定delimi ...

  6. R语言︱非结构化数据处理神器——rlist包

    本文作者:任坤,厦门大学王亚南经济研究院金融硕士生,研究兴趣为计算统计和金融量化交易,pipeR,learnR,rlist等项目的作者. 近年来,非关系型数据逐渐获得了更广泛的关注和使用.下面分别列举 ...

  7. SQL查询--简单了解SQL(结构化查询语言)

    以下内容是从其他地方摘抄过来的哈,原文地址忘记了,当时把内容记在了笔记中 SQL分类: 数据查询语言(DQL) 数据定义语言(DDL) 数据操纵语言(DML) 数据控制语言(DCL) 1.数据查询语言 ...

  8. SQL 结构化查询语言手册

    摘自该学习网站: http://www.w3school.com.cn/sql/ 新学到的几点: and 和or 连用,记得用括号.                2.SQL通配符补充   例如:   ...

  9. 基于oracle的sql(结构化查询语言)指令

    创建表空间 create tablespace 表空间名 datafile '存储路径(c:\a\a.dbf)' size 200m autoextend on next 10m maxsize un ...

随机推荐

  1. delphi三层结构常出现的问题和解决方案

    以下问题出现原因有可能多个,暂时将我遇见的记录下来,以后有新的在陆续更新上去,有网友愿意的话也可以共同测试一下. 一,无法更新定位行.一些值可能已在最后一次读取已更改. 错误出现前提: 1, 录数据时 ...

  2. Something of HTTP

    学习发现所需且所欠知识: 参考:  1.一堆博客   2.HTTP图解(链接奉上,自取)提取码: n6jq http简介 http返回状态码 http方法(点击查看) GET POST PATCH H ...

  3. Aizu 0525 Osenbei 搜索 A

    Aizu 0525 Osenbei https://vjudge.net/problem/Aizu-0525 题目: IOI製菓では,創業以来の伝統の製法で煎餅(せんべい)を焼いている.この伝統の製法 ...

  4. Nodejs之路:非I/O的异步API

    本篇主要介绍setTimeout,setInterval,setImmediate和process.nextTick. 1,定时器 Node中的定时器和浏览器中用法一致.区别在于:在Node中,执行到 ...

  5. 学习Acegi应用到实际项目中(1)

    在此,本人声明,我处于菜鸟阶段,文章的内容大部分摘自zhanjia的博客(http://zhanjia.iteye.com/category/43399),旨在学习,有很多地方,我理解不够透彻,可能存 ...

  6. 第34 memcached缓存

    1.缓存数据库 缓存:将数据存储在内存中,只有当磁盘胜任不了的时候,才会启用缓存. 缺点:断电数据丢失(双电),用缓存存储数据的目的只是为了应付大并发的业务,至于数据存储及可靠性不要找他了.   数据 ...

  7. MFC头文件

    AFX.H struct CRuntimeClass; // object type information class CObject; // the root of all objects cla ...

  8. Xutils简

    //解析 private void myinitData() { RequestParams parms=new RequestParams("http://huixinguiyu.cn/A ...

  9. 给JavaScript24条最佳实践

    作为“30 HTML和CSS最佳实践”的后续,这篇文章将回顾JavaScript的知识 !如果你看完了下面的内容,请务必让我们知道你掌握的小技巧! 1.使用 === 代替 == JavaScript ...

  10. 快速部署Apache服务静态网站

    Apache是世界使用排名第一的Web服务器软件.它可以运行在几乎所有广泛使用的计算机平台上,由于其跨平台和安全性被广泛使用,是最流行的Web服务器端软件之一.它快速.可靠并且可通过简单的API扩充, ...