主表:

从表:

结果集: 查询从表中年龄最大的一行数据,如果存在年龄相等的则为了保证唯一取id(主键)最大的一行。

一、利用sql子查询嵌套
-- --------------------------------
-- 利用sql子查询嵌套
-- --------------------------------
-- step 1. 子查询:找到每组最大的子类年龄
select parent_id,max(child_age) from child group by parent_id; -- step 2. 找到符合的行 (很可能出现重复)
select cc.* from child cc
INNER JOIN (select parent_id,max(child_age) child_age from child group by parent_id) tmp
on tmp.parent_id = cc.parent_id and tmp.child_age = cc.child_age
order by cc.parent_id,cc.child_id; -- step 3. 为了解决重复需要再加一层,取唯一标识id最大/最小的一行
select max(cc.child_id) from child cc
INNER JOIN (select parent_id,max(child_age) child_age from child group by parent_id) tmp
on tmp.parent_id = cc.parent_id and tmp.child_age = cc.child_age
group by cc.parent_id,cc.child_age -- step 4. 在3中就找到了符合条件行的id
select * from parent pa
LEFT JOIN (SELECT cc.* from child cc
INNER JOIN (select max(cc.child_id) child_id from child cc
INNER JOIN (select parent_id,max(child_age) child_age from child group by parent_id) tmp
  on tmp.parent_id = cc.parent_id and tmp.child_age = cc.child_age
group by cc.parent_id,cc.child_age) tmp on TMP.child_id = cc.child_id
) tmp on tmp.parent_id = pa.parent_id
where 1=1 ORDER BY pa.parent_id;
二、利用oracle自带的分析函数
-- --------------------------------
-- 利用oracle分析函数
-- --------------------------------
-- step-1:找到子类符合的id, DISTINCT去重
select DISTINCT first_value(cc.child_id)
over(partition by cc.parent_id order by cc.parent_id,cc.child_age desc,cc.child_id desc) child_id
from child cc;
-- step-2: 符合的子类结果集
SELECT * from child cc where cc.child_id in(
select DISTINCT first_value(cc.child_id)
over(partition by cc.parent_id order by cc.parent_id,cc.child_age desc,cc.child_id desc) child_id
from child cc
); SELECT * from child cc where EXISTS ( select 1 from (
select DISTINCT first_value(cc.child_id)
over(partition by cc.parent_id order by cc.parent_id,cc.child_age desc,cc.child_id desc) child_id
from child cc) tmp where tmp.child_id = cc.child_id
); -- step-3: 最终结果集
select * from parent pa
LEFT JOIN child cc on cc.parent_id = pa.parent_id
and cc.child_id in(
select DISTINCT first_value(cc.child_id)over(partition by cc.parent_id order by cc.parent_id,cc.child_age desc,cc.child_id desc)
from child cc)
where 1=1 ORDER BY pa.parent_id
三、分析区别

sql嵌套当然要更通用点,而且看执行计划,它的效率、消耗都要比oracle少很多;

oracle分析函数感觉还是子查询嵌套了一层,而且效率、消耗都比较高。

(才知道oracle的执行计划,完全不懂。只是看着sql嵌套查询的执行计划高效很多)

四、测试数据
-- -----------------------------
-- PARENT 父表
-- -----------------------------
CREATE TABLE "PARENT" (
"PARENT_ID" NUMBER NOT NULL ,
"PARENT_NAME" VARCHAR2(255 BYTE) NOT NULL
)
LOGGING NOCOMPRESS NOCACHE;
-- Records of PARENT
INSERT INTO "PARENT" VALUES ('', '周父');
INSERT INTO "PARENT" VALUES ('', '吴父');
INSERT INTO "PARENT" VALUES ('', '郑父');
INSERT INTO "PARENT" VALUES ('', '王父');
INSERT INTO "PARENT" VALUES ('', '赵父');
-- Checks structure for table PARENT
ALTER TABLE "PARENT" ADD CHECK ("PARENT_ID" IS NOT NULL);
ALTER TABLE "PARENT" ADD CHECK ("PARENT_NAME" IS NOT NULL); -- -----------------------------
-- PARENT 子表
-- -----------------------------
CREATE TABLE "CHILD" (
"CHILD_ID" NUMBER NOT NULL ,
"CHILD_NAME" VARCHAR2(255 BYTE) NOT NULL ,
"CHILD_AGE" NUMBER NOT NULL ,
"PARENT_ID" VARCHAR2(255 BYTE) NOT NULL
)
LOGGING NOCOMPRESS NOCACHE; -- ----------------------------
-- Records of CHILD
-- ----------------------------
INSERT INTO "CHILD" VALUES ('', '周一', '', '');
INSERT INTO "CHILD" VALUES ('', '周二', '', '');
INSERT INTO "CHILD" VALUES ('', '周三', '', ''); INSERT INTO "CHILD" VALUES ('', '吴一', '', '');
INSERT INTO "CHILD" VALUES ('', '吴二', '', '');
INSERT INTO "CHILD" VALUES ('', '吴三', '', '');
INSERT INTO "CHILD" VALUES ('', '吴四', '', ''); INSERT INTO "CHILD" VALUES ('', '郑一', '', '');
INSERT INTO "CHILD" VALUES ('', '郑二', '', ''); INSERT INTO "CHILD" VALUES ('', '王一', '', ''); -- Checks structure for table CHILD
ALTER TABLE "CHILD" ADD CHECK ("CHILD_ID" IS NOT NULL);
ALTER TABLE "CHILD" ADD CHECK ("CHILD_NAME" IS NOT NULL);
ALTER TABLE "CHILD" ADD CHECK ("CHILD_AGE" IS NOT NULL);
ALTER TABLE "CHILD" ADD CHECK ("PARENT_ID" IS NOT NULL);

测试表结构和数据

【database】oracle关联查询主表对应的特定一行从表结果集的更多相关文章

  1. Oracle关联查询-数据类型不一致问题 ORA-01722: 无效数字

    一.存在表A和表B,都包含字段user_no,但数据类型不一致,如下: create table A ( user_id varchar2(20), user_no number(12,0), xxx ...

  2. Oracle关联查询关于left/right join的那点事

    /*题外话 --更改foreign key约束定义引用行(delete cascade/delete set null/delete no action),默认delete on action--引用 ...

  3. Oracle 关联查询

    select count(1),a.policy_id from gp_pol_prod a where a.product_id=8401 group by a.policy_id having c ...

  4. oracle中查询、禁用、启用、删除表外键

    1.查询所有表的外键的: select table_name, constraint_name from user_constraints where constraint_type = 'R';   ...

  5. SQL语句关联查询

    一:连接类型: 关联查询:只有存在关联的表才能关联查询,完全独立的表之间无法关联 1.关联的类型:自关联,左关联,右关联,全关联(full join)两张表都是主表 2.关联的表:两张以上,以一张(或 ...

  6. mybatis collection 一对多关联查询,单边分页的问题总结!

    若想直接通过sql实现多级关联查询表结构得有2 个必不可少的字段:id ,parentId,levelId id:主键id, parentId:父id levelId:表示第几级(表本身关联查询的时候 ...

  7. mysql如何执行关联查询与优化

    mysql如何执行关联查询与优化 一.前言 在数据库中执行查询(select)在我们工作中是非常常见的,工作中离不开CRUD,在执行查询(select)时,多表关联也非常常见,我们用的也比较多,那么m ...

  8. mybatis实战教程二:多对一关联查询(一对多)

    多对一关联查询 一.数据库关系.article表和user表示多对一的关系 CREATE TABLE `article` ( `id` ) NOT NULL AUTO_INCREMENT, `user ...

  9. 【SQL】在SQL Server中多表关联查询问题

    好久没有写SQL语句的多表连接查询,总在用框架进行持久化操作.今天写了一个多表关联查询,想根据两个字段唯一确定一条数据 失败的案例如下: SELECT cyb.id,ad.name FROM [Gen ...

随机推荐

  1. codeforces 922 B. Magic Forest(枚举、位运算(异或))

    题目链接:点击打开链接 Imp is in a magic forest, where xorangles grow (wut?) A xorangle of order n is such a no ...

  2. Java 中序列化与反序列化

    一. 序列化和反序列化概念 Serialization(序列化)是一种将对象以一连串的字节描述的过程:反序列化deserialization是一种将这些字节重建成一个对象的过程.将程序中的对象,放入文 ...

  3. CVE-2019-0199:Apache Tomcat DDOS

    CVE-2019-0199:Apache Tomcat DDOS 0X00漏洞概述 Apache Tomcat HTTP/2拒绝服务漏洞,该漏洞是由于应用服务允许接收大量的配置流量,并且客户端在没有读 ...

  4. jenkins SSH发布文件 Publish over SSH

    jenkins 构建完成后需要一键发布,结构如下 A服务器 svn B服务器 jenkins C服务器 应用服务器 B从A拉取代码后打包成war,然后向C服务器拷贝war包 这里解决的就是远程拷贝问题 ...

  5. 内网客户 通过 公网域名/ip 访问内网web服务器 出错

    在一内部局域网中, client  内网地址为 10.0.0.2     web  服务器内网地址为 10.0.0.1    外网地址为  211.6.15.1    域名为  xx.love.com ...

  6. linux shell实用常用命令

    本文主要介绍Linux Shell的一些使用小技巧收集,非常实用,需要的朋友可以参考下. 查看本机某端口是否被占用 netstat -anpt | grep 22 查看远程某端口是否被开放 echo ...

  7. Java synchronized 关键字详解

    Java synchronized 关键字详解 前置技能点 进程和线程的概念 线程创建方式 线程的状态状态转换 线程安全的概念 synchronized 关键字的几种用法 修饰非静态成员方法 sync ...

  8. 小白学 Python 数据分析(9):Pandas (八)数据预处理(2)

    人生苦短,我用 Python 前文传送门: 小白学 Python 数据分析(1):数据分析基础 小白学 Python 数据分析(2):Pandas (一)概述 小白学 Python 数据分析(3):P ...

  9. 深入理解 Android 中的各种 Context

    前言 网上关于 Context 的文章也已经有不少了,比如值得参考的有: Android Context完全解析,你所不知道的Context的各种细节 Android Context 到底是什么? 但 ...

  10. mysql随机抽取数据

      -- 慢 ; -- 较慢 SELECT * FROM `table` WHERE id >= (SELECT floor( RAND() * ((SELECT MAX(id) FROM `t ...