开发指南—DQL语句—子查询

简介: 本文介绍PolarDB-X支持的子查询类别及在PolarDB-X中使用子查询的相关限制和注意事项。

本文介绍PolarDB-X支持的子查询类别及在PolarDB-X中使用子查询的相关限制和注意事项。

使用限制

相比原生MySQL,PolarDB-X在子查询使用上增加了如下限制:

  • 不支持在HAVING子句中使用子查询,示例如下:
SELECT name, AVG( quantity )
FROM tb1
GROUP BY name
HAVING AVG( quantity ) > 2* (
   SELECT AVG( quantity )
   FROM tb2
 );
  • 不支持在JOIN ON子句中使用子查询,示例如下:
SELECT * FROM tb1 p JOIN tb2 s on (p.id=s.id and p.quantity>All(select quantity from tb3))
  • 等号操作行符的标量子查询(The Subquery as Scalar Operand)不支持ROW语法。示例如下:
select * from tb1 where row(id, name) = (select id, name from tb2)
  • 不支持在UPDATE SET子句中使用子查询,示例如下:
UPDATE t1 SET c1 = (SELECT c2 FROM t2 WHERE t1.c1 = t2.c1) LIMIT 10

注意事项

PolarDB-X中部分子查询仅能以APPLY的方式执行,查询效率低下。在实际使用中请尽量避免如下例子中的低效SQL:

  • WHERE条件中OR与子查询共存时,执行效率会依外表数据情况大幅降低。示例如下:
高效:select * from tb1 where id in (select id from tb2)

高效:select * from tb1 where id in (select id from tb2) and id>3
低效:select from tb1 where id in (select id from tb2) or id>3
  • 关联子查询(Correlated Subqueries)的关联项中带函数或非等号运算符。示例如下:
高效:select  from tb1 a where id in
(select id from tb2 b where a.name=b.name)
低效:select * from tb1 a where id in
(select id from tb2 b where UPPER(a.name)=b.name)
低效:select * from tb1 a where id in
(select id from tb2 b where a.decimal_test=abs(b.decimal_test))
低效:select * from tb1 a where id in
(select id from tb2 b where a.name!=b.name)
低效:select * from tb1 a where id in
(select id from tb2 b where a.name>=b.name)
  • 关联子查询(Correlated Subqueries)关联项与其它条件的逻辑运算符为OR。示例如下:
高效:select * from tb1 a where id in
(select id from tb2 b where a.name=b.name
and b.date_test<'2015-12-02')
低效:select * from tb1 a where id in
(select id from tb2 b where a.name=b.name
or b.date_test<'2015-12-02')
低效:select * from tb1 a where id in
(select id from tb2 b where a.name=b.name
or b.date_test=a.date_test)
  • 标量子查询(The Subquery as Scalar Operand)带关联项。示例如下:
高效:select * from tb1 a where id >
(select id from tb2 b where b.date_test<'2015-12-02')
低效:select * from tb1 a where id >
(select id from tb2 b where a.name=b.name
and b.date_test<'2015-12-02')
  • 跨关联层子查询。示例如下:
    • SQL多层关联,每层子查询关联项仅与直接上层关联,此类高效。
高效:select * from tb1 a where id in(select id from tb2 b 
where a.name=b.name and
exists (select name from tb3 c where b.address=c.address))
    • SQL多层关联,但表c的子查询关联项中与表a的列进行了关联,此类低效。
低效:select * from tb1 a where id in(select id from tb2 b 
where a.name=b.name and
exists (select name from tb3 c where a.address=c.address))
  • 说明 上述示例中,表a表b表b表c为直接层级关联,表a表c间为跨层关联。
  • 子查询中包含GROUP BY,请确保GROUP BY的分组列包含关联项。示例如下:
    • SQL子查询中包含聚合函数和关联项,关联项b.pk包含于分组列pk之中,此类高效。
高效:select * from tb1 a where exists 
(select pk from tb2 b
where a.pk=b.pk and b.date_test='2003-04-05'
group by pk);
    • SQL子查询中包含聚合函数和关联项,关联项b.date_test不包含于分组列pk之中,此类低效。
低效:select * from tb1 a where exists 
(select pk from tb2 b
where a.date_test=b.date_test and b.date_test='2003-04-05'
group by pk);

支持的子查询

PolarDB-X目前支持如下类别的子查询:

  • Comparisons Using SubqueriesComparisons Using Subqueries指带有比较运算符的子查询,这类子查询最为常见。
    • 语法
non_subquery_operand comparison_operator (subquery)
comparison_operator: = > < >= <= <> != <=> like
    • 示例
select * from tb1 WHERE 'a' = (SELECT column1 FROM t1)

    • 说明 目前仅支持子查询在比较运算符的右边。
  • Subqueries with ANY、ALL、IN/NOT IN、EXISTS/NOT EXISTS
    • 语法
operand comparison_operator ANY (subquery)
operand comparison_operator ALL (subquery)
operand IN (subquery)
operand NOT IN (subquery)
operand EXISTS (subquery)
operand NOT EXISTS (subquery)
comparison_operator:= > < >= <= <> !=
    • 示例
      • ANY:如果子查询返回的任意一行满足ANY前的表达式,返回TRUE,否则返回FALSE。
      • ALL:如果子查询返回所有行都满足ALL前的表达式,返回TRUE,否则返回FALSE。
      • IN:在子查询前使用时,IN等价于=ANY。示例如下:
SELECT s1 FROM t1 WHERE s1 = ANY (SELECT s1 FROM t2);
SELECT s1 FROM t1 WHERE s1 IN (SELECT s1 FROM t2);
      • NOT IN:NOT IN在子查询前使用时,等价于<>ALL。示例如下:
SELECT s1 FROM t1 WHERE s1 <> ALL (SELECT s1 FROM t2);
SELECT s1 FROM t1 WHERE s1 NOT IN (SELECT s1 FROM t2);
      • EXISTS:如果子查询返回任意行,EXISTS子查询结果为TRUE;如果子查询返回空值,EXISTS子查询结果为FALSE。示例如下:
SELECT column1 FROM t1 WHERE EXISTS (SELECT  FROM t2);

      • 说明 如果EXISTS子查询中包含任意行,即使只包含NULL的行值,WHERE条件也会返回TRUE。
      • NOT EXISTS:如果子查询返回任意行,NOT EXISTS子查询结果为FALSE;如果子查询返回空值,NOT EXISTS子查询结果为TRUE。
  • Row Subqueries
    • Row Subqueries支持如下比较运算符:
comparison_operator:=  >  <  >=  <=  <>  !=  <=>
    • 示例
SELECT  FROM t1
WHERE (col1,col2) = (SELECT col3, col4 FROM t2 WHERE id = 10);
SELECT * FROM t1
WHERE ROW(col1,col2) = (SELECT col3, col4 FROM t2 WHERE id = 10);
    • 以上两个SQL是等价的,只有同时满足以下条件时,t1表的数据行才会返回:
      • 子查询(SELECT col3, col4 FROM t2 WHERE id=10 )仅返回一行记录,返回多行会报错。
      • 子查询返回的col3col4结果与主表中col1col2的值需一一对应。
  • Correlated SubqueriesCorrelated Subqueries指子查询中包含对外层查询表的引用。示例如下:
SELECT * FROM t1
WHERE column1 = ANY (SELECT column1 FROM t2
WHERE t2.column2 = t1.column2);
  • 示例子查询SQL中并没有包含表t1及其列名column2,此时会向上一层寻找表t1的引用。
  • Derived Tables(Subqueries in the FROM Clause)Derived Tables指在FROM子句中的子查询。
    • 语法
SELECT ... FROM (subquery) [AS] tbl_name ...
    • 示例
      1. 数据准备:使用如下语法创建表t1:
CREATE TABLE t1 (s1 INT, s2 CHAR(5), s3 FLOAT);
INSERT INTO t1 VALUES (1,'1',1.0);
INSERT INTO t1 VALUES (2,'2',2.0);
      1. 使用如下查询并得到查询结果为2, '2', 4.0
SELECT sb1,sb2,sb3
FROM (SELECT s1 AS sb1, s2 AS sb2, s3*2 AS sb3 FROM t1) AS sb
WHERE sb1 > 1;
      1. 查询需求:获取分组数据SUM后的平均值。若直接使用如下SQL则会报错,无法执行:
SELECT AVG(SUM(s1)) FROM t1 GROUP BY s1;
      1. 此时可使用如下Derived Tables子查询,并得到查询结果为1.5000
SELECT AVG(sum_s1)
FROM (SELECT SUM(s1) AS sum_s1
FROM t1 GROUP BY s1) AS t1;
      1. 说明
        • Derived Tables必须拥有一个别名(如示例中的t1)。
        • Derived Tables可以返回一个标量、列、行或表。
        • Derived Tables不可以成为Correlated Subqueries,即不能包含子查询外部表的引用。
相关文章
搭建一个简单的直播网站
我是一个比较爱看直播的人,经常空闲的时候会看一看LOL、吃鸡的直播。正好最近在研究阿里云的视频直播服务,突发奇想,自己来搭建一个简单的直播平台!主要会用到的东西有:视频直播、ECS、OBS、阿里播放器。
10786 1
|
安全 Linux 数据安全/隐私保护
Intel TME和MKTME技术解析
# 市场需求 人们对透明全内存加密这个功能的需求主要来自对机密和敏感数据的保护。普通RAM里面储存的数据,在掉电之后,一般都以为是彻底消失了。但其实在一些复杂的离线攻击下,这些数据仍然是能被恢复出来并导致泄密;而持久性存储器(即外存,包括磁盘、SSD、eMMC等)的数据更加容易泄露。这些设备可能有硬件锁机制的保护,但是用户其实希望的是更细粒度的保护,比如per进程/容器/VM级的。 Int
5964 0
Intel TME和MKTME技术解析
|
JSON 搜索推荐 API
抖音商品详情API接口:获取商品信息的指南
抖音商品详情API接口由抖音开放平台提供,允许第三方应用访问抖音小店的商品数据,包括基本信息、价格、库存及用户评价等。其优势在于数据实时性、自动化处理、市场分析及个性化推荐。通过注册账号、获取API密钥、阅读文档和构建请求,用户可高效获取商品信息,提升运营效率。未来,该接口将在电商领域发挥更大作用。
|
11月前
|
网络协议 安全 测试技术
Nping工具详解:网络工程师的瑞士军刀
### Nping工具详解:网络工程师的瑞士军刀 Nping是Nmap项目的一部分,支持TCP、UDP、ICMP和ARP等多种协议,用于生成和分析网络数据包。它提供灵活的命令行界面,适用于网络探测、安全测试和故障排除。本文介绍Nping的基础与高级用法,包括发送不同类型的网络请求、自定义TCP标志位、路由跟踪等,并通过实战案例展示其应用。掌握Nping有助于更好地理解和管理网络环境。 (239字符)
901 9
|
12月前
|
搜索推荐 物联网 PyTorch
Qwen2.5-7B-Instruct Lora 微调
本教程介绍如何基于Transformers和PEFT框架对Qwen2.5-7B-Instruct模型进行LoRA微调。
12555 34
Qwen2.5-7B-Instruct Lora 微调
|
人工智能 算法 安全
基于YOLOV8的骑行智能守护实时检测系统【训练和系统源码+Pyside6+数据集+包运行】
基于YOLOv8的骑行智能守护实时检测系统,通过图像处理和AI技术,实时监测电动车及骑行者头盔佩戴情况,提升道路安全。该系统支持图片、视频和摄像头实时检测,具备GUI界面,便于操作和展示结果。使用5448张真实场景图片训练,包含电动车和骑行者是否佩戴头盔的三类标注。系统基于Python和Pyside6开发,具备模型权重导入、检测置信度调节等功能。
906 0
基于YOLOV8的骑行智能守护实时检测系统【训练和系统源码+Pyside6+数据集+包运行】
|
人工智能 前端开发 算法
【2023五福】创新科技与传统年俗的有机融合 - AI 年画
23 年兔年,五福项目将传统的写福字升级成了年画,用户通过绘制兔子轮廓可以得到活动的兔子,同时由 AI 生成对应的兔子年画,整个过程给用户带来很强的惊喜感,同时将具有传统氛围的年画与科技感拉满的 AI 作图有机结合,为大家带来全新的年俗体验。AI 年画作为 23 兔年五福的创新项目,在玩法和技术方案上都采用全新的实现,前后端技术、AI 算法深度,以及美术互动等深度协同,实现了玩法了技术的双创新,最
【2023五福】创新科技与传统年俗的有机融合 - AI 年画
|
存储 域名解析 监控
云上攻防:任意上传、域名接管与AK/SK泄漏
随着企业上云的趋势加剧,云安全成为新的焦点。本文探讨了云计算环境中的三大安全问题:任意上传、域名接管与AK/SK泄漏,分析了这些威胁的工作原理及防护措施,强调了数据保护和访问控制的重要性。通过阿里云等平台的实际案例,提供了具体的安全防范建议。
1648 2
云上攻防:任意上传、域名接管与AK/SK泄漏
|
机器学习/深度学习 编解码 人工智能
视频分辨率的历史发展,未来趋势是什么?
随着技术的不断发展,视频分辨率也在不断提高。视频分辨率是指视频图像中可显示的像素数量,通常表示为水平像素数和垂直像素数。它对于观看视频时的清晰程度和细节呈现有着重要的影响。 本文将会介绍视频分辨率的基本概念,包括单位、历史发展、标准和未来趋势。我们还会探讨视频分辨率对观影体验的影响以及如何选择适合自己设备的视频分辨率。 无论您是电影爱好者还是普通用户,通过本文,您将能够了解到视频分辨率在过去的发展历程和未来的趋势,从而更好地使用和享受视频娱乐。
视频分辨率的历史发展,未来趋势是什么?
阿里云商标注册申请进度查询攻略来了
阿里云商标注册申请进度查询(太简单了),阿里云商标申请进度查询可以通过手机微信接收商标申请进度信息,在阿里云公众号“阿里云企航”中即可接收商标注册申请进度查询。商标注册申请提交到商标局后需要长达数月的审查过程,实时查询商标注册进度是十分必要的,阿里云百科分享阿里云商标注册申请进度查询方法:
1715 1
阿里云商标注册申请进度查询攻略来了