SparkSQL之AstBuilder

news2024/11/19 11:27:49

Spark SQL是基于ANTLR实现的,前文中有关于ANTLR的介绍文章《ANTLR实战》和《设计模式之访问者模式》,这篇文章主要介绍的内容是AstBuilder类。

Catalyst中提供了直接面向用户的ParseInterface接口,该接口中包含了对SQL语句、Expression表达式和TableIdentifier数据表标识符的解析方法。AbstractSqlParser是实现了ParseInterface的虚类,其中定义了返回AstBuilder的函数。

整个SQL解析相关的实现如下图所示,其中CatalystSqlParser仅用于Catalyst内部,而SparkSqlParser用于外部调用。其中,比较核心的是AstBuilder,它继承了ANTLR4生成的默认SqlBaseBaseVisitor,用于生成SQL对应的抽象语法树AST(UnresolvedLogicalPlan);SparkSqlAst-Builder继承AstBuilder,并在其基础上定义了一些DDL语句的访问操作,主要在SparkSqlParser中调用。
在这里插入图片描述
当面临开发新的语法支持时,首先需要改动的是ANTLR4文件(在SqlBase.g4中添加文法),重新生成词法分析器(SqlBaseLexer)、语法分析器(SqlBaseParser)和访问者类(SqlBaseVisitor接口与SqlBaseBaseVisitor类),然后在AstBuilder等类中添加相应的访问逻辑,最后添加执行逻辑。

为加深理解Spark SQL生成的语法树结构,可以将Spark SQL编译器部分剥离出来,构造一个类似AstBuilder的访问者类MyVisitor,在实现的访问方法中输出visitor访问操作。类似于下面的代码逻辑,实现SqlBaseBaseVisitor中的所有方法。

public class MyVisitor extends SqlBaseBaseVisitor<String>{

    public String visitSingleStatement(SqlBaseParser.SingleStatementContext ctx) {
        System.out.println("visitSingleStatement");
        return visitChildren(ctx);
    }
   .........................
}

MyVisitor中访问方法的类型为String(AstBuilder中的SqlBaseBaseVisitor为AnyRef类型,返回LogicalPlan类型),但不会返回字符串,仅用于输出访问的路径和对AST的理解。构造上述访问者类之后,接下来还需要构造一个Driver程序来驱动上述访问过程,测试下面的SQL语句。

SELECT name FROM student WHERE age > 18

为了便于理解Spark SQL的解析过程,可看GitHub上的项目 ANTLR4-SqlBase。

在Catalyst中,SQL语句经过解析,生成的抽象语法树节点都以Context结尾来命名。如下图所示为案例SQL语句生成的抽象语法树。
在这里插入图片描述
从语法树可以看到,SingleStatementContext是根节点,但是在访问该节点时一般什么都不做,只递归访问子节点。整个遍历访问操作中比较重要的是包含多个子节点的节点。例如QuerySpecificationContext节点,一般将数据表和具体的查询表达式整合在一起。左边的一系列节点对应select表达式中选择的列,中间的From ClauseContext为根节点的系列节点对应数据表,右边的一系列节点则对应where条件中的表达式。

上述语法树的结构比较通用,其他类型的SQL语句生成的语法树大同小异,这里假设在上述语句中加入排序的操作。

SELECT name FROM student WHERE age > 18 order by id desc

加入排序操作后生成的语法树如图4.5所示,可以看到新的语法树在QueryOrganization-Context节点下面加入了SortItem Context节点,代表数据查询之后所进行的排序操作。一般来讲,QueryOrganizationContext为根节点所代表的子树中包含了各种对数据组织的操作,例如Sort、Lim it和W indow算子等。
在这里插入图片描述
从上面案例可以看出,即使非常简单的SQL语句,其语法树的节点也非常多。特别是当查询涉及聚合操作、Join操作和嵌套的子查询时,整棵语法树会变得非常庞大,难以一次完成展示。

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

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

相关文章

DDD(领域驱动设计) 核心概念浅析

文章目录 DDD(领域驱动设计) 核心概念浅析前言贫血模型什么是贫血模型贫血模型的优点贫血模型的缺点 充血模型充血模型的优点充血模型的缺点 DP 概念抽象接口简单概念简单概念流程&#xff1a;实现 统一语言和模型价值DP 和 Entity 的区别 Aggregate&#xff08;聚合&#xff0…

HackTheBox - 学院【CPTS】复习1 - PASSWORD ATTACKS

前言 有一个月时间没发文章了&#xff0c;我在6月11号进入htb学院学习CPTS&#xff0c;在扎实的THM基础的加持下&#xff0c;我学的非常顺利&#xff0c;其实大部分内容都相当于复习&#xff0c;而学到的内容只是一些可能不太常见、又或者非常细节的小技巧&#xff0c;这也是非…

vscode 出现 No such file or directory 的解决办法(python tkinter)

问题 Traceback (most recent call last): File “e:\Github\Python-GUI\PyQt-Fluent-Widgets\examples\navigation\demo.py”, line 202, in w Window() File “e:\Github\Python-GUI\PyQt-Fluent-Widgets\examples\navigation\demo.py”, line 95, in init self.initWindo…

ThreadPoolExecutor源码剖析

ThreadPoolExecutor源码涉及到的内容比较多&#xff0c;需要一点点的去啃和查看… ThreadPoolExecutor的核心属性 ThreadPoolExecutor的核心属性主要就是CTL。基于CTL获取到线程池的状态以及工作线程个数。 ctl是一个int类型的整数&#xff0c;內部基于AtomicInteger&#xff0…

再谈StringBuilder为什么线程不安全以及带来的问题

1 缘起 比较有意思的是&#xff0c;学习锁消除的过程中&#xff0c;有人讲到StringBuffer在方法内构建&#xff0c;不会被其他方法引用时&#xff0c;StringBuffer的锁会被消除&#xff0c; 于是&#xff0c;顺便看了一下同源的StringBuidler为什么线程不安全&#xff0c;以及…

【无标题】TP-LINK XDR5470 WiFi6路由器 简单开箱评测

TL-XDR5470易展版AX5400双频WiFi6路由器 简单开箱测评&#xff0c;上次买的XDR6078覆盖不够&#xff0c;还是得每层再买一个&#xff0c;所以又买了个TL-XDR5470&#xff0c;支持易展mesh。 上次买的XDR6078没有外置FEM功放芯片&#xff0c;所以信号差了一点&#xff0c;得加2…

PE系统盘制作

目录 前言 制作PE盘的步骤如下 前言 PE盘是一个轻量级的系统&#xff0c;类似于Windows系统。当您的计算机无法进入Windows系统时&#xff0c;您可以通过启动PE盘来访问一个独立的操作系统&#xff0c;从而执行各种任务&#xff0c;例如拷贝重要文件或进行系统安装。PE盘通常…

win10查看端口是否被占用,被哪一个程序占用(图文)

window系统中有时候我们会出现需要的端口号被占用&#xff0c;但不知道具体是哪个程序占用的。这时我们需要找到使用此端口的程序。 方法如下&#xff1a; 1&#xff09;以管理员身份打开命令提示符窗口&#xff08;开始-运行&#xff09;。 2&#xff09;使用命令查看端口使…

R730直通Tesla P40显卡

本次讲述如何在R730的ESXi上&#xff0c;将Tesla P40直通到centos7.7和WinServer2016。使用直通模式&#xff0c;安装普通的驱动即可&#xff0c;不需要vGPU的驱动。 按计划本来后面要自己装一下系统、做RAID的&#xff0c;不过最近需要用到显卡&#xff0c;所以先把显卡安装上…

初探Flink的Java实现流处理和批处理

端午假期&#xff0c;夏日炎炎&#xff0c;温度连续40度以上&#xff0c;在家学习Flink相关知识&#xff0c;记录下来&#xff0c;方便备查。 开发工具&#xff1a;IntelliJ Idea Flink版本&#xff1a;1.13.0 本次主要用Flink实现批处理&#xff08;DataSet API&#xff09; 和…

SAM与Prompt的结合

1. SAM介绍 由Meta AI Research开发的Segment anything model&#xff08;简称SAM&#xff09;最近引起了广泛的关注。SAM在超过10亿个mask的大型分割数据集上进行了训练&#xff0c;能够在特定的图像上分割任何对象。在最初的SAM工作中&#xff0c;作者们使用了零样本迁移任务…

08- c语言字符串 (C语言)

一 字符串的定义及基本使用 1、什么是字符串 被双引号引用的字符集合&#xff01;例如&#xff1a;”hello” 、”world”&#xff0c;或者是以 \0 结尾的字符数组&#xff01;&#xff01;&#xff01; 比如&#xff1a;char ch[] {h, e, \0} 注意&#xff1a;”hello” 中…

GB50149-2010电气装置安装工程母线装置施工及验收规范

为了确保强硬钢丝绳金属封闭体绝缘金属封闭母线、绝缘子、硬件、穿墙套管等设备母线的安装质量,加快安装技术的进步,和确保设备的安全运行,使该规范。 本规范适用于总线设备安装了750 kv及以下的T范围施工和验收。 母线的安装应按照批准的设计文件施工。 设备和设备运输、储…

python:并发编程(二十五)

前言 本文将和大家一起探讨python并发编程的实际项目&#xff1a;win图形界面应用&#xff08;篇七&#xff0c;共八篇&#xff09;&#xff0c;系列文章将会从零开始构建项目&#xff0c;并逐渐完善项目&#xff0c;最终将项目打造成适用于高并发场景的应用。 本文为python并…

postman 文档、导出json脚本 导出响应数据 response ,showdoc导入postman json脚本 导出为文档word或markdown

生成文档 Collections中 选中文件夹 - ... (文件夹 功能小按钮) - view documentation : 保存响应数据 Response&#xff1a;&#xff08;如果导出接口数据&#xff0c;会同步导出响应数据&#xff09; 请求接口后&#xff0c;点击下方 Save as Example 可以保存响应数…

机器学习day20(前向传播的向量化代码,矩阵乘法)

前向传播的循环代码与向量化代码的对比 把X、B写作二维数组&#xff0c;即矩阵左边的for循环就可以用右边的np.matmul来实现matmul是numpy执行矩阵乘法的一种方式注意&#xff1a;此时所有的变量&#xff08;X、W、B、Z、A_out&#xff09;都是二维数组&#xff0c;即矩阵 向…

基础排序算法【归并排序+非递归版本+边界修正】

基础排序算法【归并排序非递归版本边界修正】 Ⅰ.归并排序(递归版本)①.分割②.归并③.拷贝 Ⅱ.非递归版本Ⅲ.边界修正 Ⅰ.归并排序(递归版本) 递归排序&#xff0c;采用的是分治法。分成子问题来处理。先让序列不断分割成子序列&#xff0c;当子序列有序后再合并。 对于一段…

Yolov5-Face 原理解析及算法解析

YOLOv5-Face 文章目录 YOLOv5-Face1. 为什么人脸检测 一般检测&#xff1f;1.1 YOLOv5Face人脸检测1.2 YOLOv5Face Landmark 2.YOLOv5Face的设计目标和主要贡献2.1 设计目标2.2 主要贡献 3. YOLOv5Face架构3.1 模型架构3.1.1 模型示意图3.1.2 CBS模块3.1.3 Head输出3.1.4 stem…

202320读书笔记|《宋词》——竹杖芒鞋轻胜马,谁怕?一蓑烟雨任平生

202320读书笔记&#xff5c;《宋词》——竹杖芒鞋轻胜马&#xff0c;谁怕&#xff1f;一蓑烟雨任平生 《宋词》韩震主编&#xff0c;偶然从书友那加入书架的书。宋词挺喜欢李清照的词以及知否的《菩萨蛮》。诗集&#xff0c;词&#xff0c;俳句&#xff0c;短歌我都很喜欢&…

工欲善其事,必先利其器-基于ubuntu18.04 VScode开发100ASK-ESP32

点击上方“嵌入式应用研究院”&#xff0c;选择“置顶/星标公众号” 干货福利&#xff0c;第一时间送达&#xff01; 来源 | 嵌入式应用研究院 整理&排版 | 嵌入式应用研究院 前面我们基于ubuntu环境搭建了esp-idf的开发环境&#xff0c;它也是为了接下来基于VSCode来开发1…