从选择列表中的引用表中选择第 N 行的一列
Posted
技术标签:
【中文标题】从选择列表中的引用表中选择第 N 行的一列【英文标题】:Selecting one column of the Nth row from a refernced table in the select list 【发布时间】:2019-02-14 13:09:42 【问题描述】:我有两个表:cross_section 和 layer。
每个横截面都有多个层,依次有一个位置和一个汇总列。位置(整数)用于对每个横截面的层进行排序,但不必连续(例如 10、20、40)。
我需要将查询扩展到 cross_section 表,以包含每个横截面层的摘要(固定数 > 1),保留位置属性定义的顺序。
大部分 SQL 都是自动生成的;我只能将包含子查询的额外元素添加到选择列表中。 这是自动生成的 SQL 的样子:
select cs.*, [first layer summary], [second layer summary]... from cross_section cs;
我尝试了多种不同的方法,但都没有按预期工作(也许这根本不可能)。
我当前的非工作状态如下所示:
---------------generated------------------------------------------
select cs.*,
---------------partial statment for clumn one---------------------
(select summary
from (select summary, l.cs_id
from layer l order by layer_position)
where cross_section.id like cs_id and rownum=1) layer_summary_1,
---------------partial statment for clumn two---------------------
(select summary
from (select summary, l.cs_id
from layer l order by layer_position)
where cross_section.id like cs_id and rownum=2) layer_summary_2
---------------generated------------------------------------------
from cross_section cs;
现在,除了第一个位置之外的任何内容都返回为 null。
编辑: 示例输出,按要求:
CSID, Stuff from cross section, layer_summary_1, layer_summary_2
12345, ..., stuff (null)
【问题讨论】:
分享样本和输出 【参考方案1】:问题是这个子句:rownum=2
。
rownum
伪列枚举生成的结果集中的行。所以有一个 rownum = 1
返回一行;这就是为什么您发现第一个位置按预期返回的原因。但永远不可能有rownum = 2
。 (rownum <= 2
返回两行,因为有一行 rownum = 1
。)
解决方案很简单:在子查询中使用解析 row_number()
函数,您可以在主 WHERE 子句中引用该函数:
---------------generated------------------------------------------
select cs.*,
---------------partial statment for clumn one---------------------
(select summary
from (select summary, l.cs_id
, row_number() over (order by layer_position) as rn
from layer l order by layer_position)
where cross_section.id like cs_id and rn=2)
---------------partial statment for clumn two---------------------
(select summary
from (select summary, l.cs_id
, row_number() over (order by layer_position) as rn
from layer l order by layer_position)
where cross_section.id like cs_id and rn=2)
---------------generated------------------------------------------
from cross_section cs;
您的问题对数据或业务逻辑不清楚,因此上述可能会产生不正确的结果。如果是这样,您需要通过添加 PARTITION BY 条件来调整窗口子句。如:
, row_number() over (partition by cs_id order by layer_position) as rn
【讨论】:
谢谢,帮了大忙。正如你所怀疑的,我需要调整 window 子句。以上是关于从选择列表中的引用表中选择第 N 行的一列的主要内容,如果未能解决你的问题,请参考以下文章
更好的方法来选择第一个表中的所有列,并且只选择第二个表中的一列。