MySQL解析器源码分析--对select语句中子查询处理逻辑的分析(二)

本文涉及的产品
云数据库 RDS MySQL Serverless,0.5-2RCU 50GB
简介:

(接上文)

下面以一个简单的SQL作为例子来讲解。

例如: Select * from tt where tt.id in (select id from tt1) union select * from tt1;

SQL在经过解析后的类间关系如下图:


 

 

MySQL解析器相关处理逻辑

 

MySQL解析器在分析到SQL存在union或者select子句,from子句,where子句中的subselect时,都会调用mysql_new_select函数维护上述所讲的数据结构,区别是union在调用mysql_new_select时传第二个参数move_down=0;subselect在调用mysql_new_select时传第二个参数move_down=1。

 

mysql_new_select函数具体解释如下:

 

Code:
bool mysql_new_select(LEX *lex, bool move_down)
{
      SELECT_LEX *select_lex;
      THD *thd= lex->thd;
      DBUG_ENTER("mysql_new_select");

//为子查询新建一个SELECT_LEX即st_select_lex,这个st_select_lex可能对应遇到的select子句,from子句,

//where子句中的subselect或者union关系中的select子句;

if (!(select_lex= new (thd->mem_root) SELECT_LEX())) DBUG_RETURN(1); select_lex->select_number= ++thd->select_number; select_lex->parent_lex= lex; /* Used in init_query. */ select_lex->init_query(); select_lex->init_select(); lex->nest_level++; if (lex->nest_level > (int) MAX_SELECT_NESTING) { my_error(ER_TOO_HIGH_LEVEL_OF_NESTING_FOR_SELECT,MYF(0),MAX_SELECT_NESTING); DBUG_RETURN(1); } select_lex->nest_level= lex->nest_level; if (thd->stmt_arena->is_stmt_prepare()) select_lex->uncacheable|= UNCACHEABLE_PREPARE; //如果move_down=1,即是为select子句,from子句,where子句中的subselect创建相应数据结构时 if (move_down) { SELECT_LEX_UNIT *unit; lex->subqueries= TRUE; //新建一个SELECT_LEX_UNIT即st_select_lex_unit if (!(unit= new (thd->mem_root) SELECT_LEX_UNIT())) DBUG_RETURN(1); unit->init_query(); unit->init_select(); unit->thd= thd; //将此SELECT_LEX_UNIT挂在上一级select语句对应SELECT_LEX的下,即此SELECT_LEX的slave指针指向此SELECT_LEX_UNIT unit->include_down(lex->current_select); unit->link_next= 0; unit->link_prev= 0; unit->return_to= lex->current_select;

//同时将这个subselect对应的SELECT_LEX挂在刚建的这个SELECT_LEX_UNIT下,这里MySQL对于select子句,from子句,where子句

//中可能出现的subselect,都会先新建一个SELECT_LEX_UNIT挂在上一级select语句对应的SELECT_LEX下,

//同时建一个subselect对应的SELECT_LEX挂在SELECT_LEX_UNIT下。

//这样如果这个subselect的右边又出现了一个subselect和它进行union操作,可以将右边的这个subselect对应的

//SELECT_LEX放在上一级的SELECT_LEX_UNIT表达这个union关系。

select_lex->include_down(unit); select_lex->context.outer_context= &select_lex->outer_select()->context; } //如果move_down=0;意味着对应处理的是union关系 else { if (lex->current_select->order_list.first && !lex->current_select->braces) { my_error(ER_WRONG_USAGE, MYF(0), "UNION", "ORDER BY"); DBUG_RETURN(1); }

//将要处理这个新的参与union中的select子句对应的SELECT_LEX加入union链表中,union操作符左边这个select子句对应的

//SELECT_LEX已经在这个链表中

select_lex->include_neighbour(lex->current_select); SELECT_LEX_UNIT *unit= select_lex->master_unit(); if (!unit->fake_select_lex && unit->add_fake_select_lex(lex->thd)) DBUG_RETURN(1); select_lex->context.outer_context= unit->first_select()->context.outer_context; } select_lex->master_unit()->global_parameters= select_lex; select_lex->include_global((st_select_lex_node**)&lex->all_selects_list); lex->current_select= select_lex; select_lex->context.resolve_in_select_list= TRUE; DBUG_RETURN(0); }










本文转自百度技术51CTO博客,原文链接:http://blog.51cto.com/baidutech/748849,如需转载请自行联系原作者

相关实践学习
基于CentOS快速搭建LAMP环境
本教程介绍如何搭建LAMP环境,其中LAMP分别代表Linux、Apache、MySQL和PHP。
全面了解阿里云能为你做什么
阿里云在全球各地部署高效节能的绿色数据中心,利用清洁计算为万物互联的新世界提供源源不断的能源动力,目前开服的区域包括中国(华北、华东、华南、香港)、新加坡、美国(美东、美西)、欧洲、中东、澳大利亚、日本。目前阿里云的产品涵盖弹性计算、数据库、存储与CDN、分析与搜索、云通信、网络、管理与监控、应用服务、互联网中间件、移动服务、视频服务等。通过本课程,来了解阿里云能够为你的业务带来哪些帮助     相关的阿里云产品:云服务器ECS 云服务器 ECS(Elastic Compute Service)是一种弹性可伸缩的计算服务,助您降低 IT 成本,提升运维效率,使您更专注于核心业务创新。产品详情: https://www.aliyun.com/product/ecs
相关文章
|
10天前
|
关系型数据库 MySQL 索引
mysql 分析5语句的优化--索引添加删除
mysql 分析5语句的优化--索引添加删除
11 0
|
1月前
|
关系型数据库 MySQL
【MySQL】——Select查询语句知识点练习(其一)
【MySQL】——Select查询语句知识点练习(其一)
36 0
|
21天前
|
SQL 关系型数据库 MySQL
【MySQL技术专题】「问题实战系列」深入探索和分析MySQL数据库的数据备份和恢复实战开发指南(8.0版本升级篇)
【MySQL技术专题】「问题实战系列」深入探索和分析MySQL数据库的数据备份和恢复实战开发指南(8.0版本升级篇)
94 0
|
10天前
|
SQL 缓存 关系型数据库
mysql性能优化-慢查询分析、优化索引和配置
mysql性能优化-慢查询分析、优化索引和配置
76 0
|
16天前
|
缓存 关系型数据库 MySQL
MySQL 查询优化:提速查询效率的13大秘籍(索引设计、查询优化、缓存策略、子查询优化以及定期表分析和优化)(中)
MySQL 查询优化:提速查询效率的13大秘籍(索引设计、查询优化、缓存策略、子查询优化以及定期表分析和优化)(中)
|
2月前
|
SQL 关系型数据库 MySQL
MySQL技能完整学习列表10、数据导入和导出——1、数据导入(LOAD DATA, mysqldump)——2、数据导出(SELECT ... INTO OUTFILE, mysqldump)
MySQL技能完整学习列表10、数据导入和导出——1、数据导入(LOAD DATA, mysqldump)——2、数据导出(SELECT ... INTO OUTFILE, mysqldump)
48 0
|
16天前
|
存储 关系型数据库 MySQL
MySQL 查询优化:提速查询效率的13大秘籍(避免使用SELECT *、分页查询的优化、合理使用连接、子查询的优化)(上)
MySQL 查询优化:提速查询效率的13大秘籍(避免使用SELECT *、分页查询的优化、合理使用连接、子查询的优化)(上)
|
18天前
|
SQL 关系型数据库 MySQL
【MySQL】慢SQL分析流程
【4月更文挑战第1天】【MySQL】慢SQL分析流程
|
21天前
|
SQL 关系型数据库 MySQL
【MySQL技术专题】「问题实战系列」深入探索和分析MySQL数据库的数据备份和恢复实战开发指南(数据恢复补充篇)(一)
【MySQL技术专题】「问题实战系列」深入探索和分析MySQL数据库的数据备份和恢复实战开发指南(数据恢复补充篇)
29 0
|
1月前
|
存储 关系型数据库 MySQL
TiDB与MySQL、PostgreSQL等数据库的比较分析
【2月更文挑战第25天】本文将对TiDB、MySQL和PostgreSQL等数据库进行详细的比较分析,探讨它们各自的优势和劣势。TiDB作为一款分布式关系型数据库,在扩展性、并发性能等方面表现突出;MySQL以其易用性和成熟性受到广泛应用;PostgreSQL则在数据完整性、扩展性等方面具有优势。通过对比这些数据库的特点和适用场景,帮助企业更好地选择适合自己业务需求的数据库系统。

推荐镜像

更多