当前位置: 首页 > 知识库问答 >
问题:

选择一行,其中包含多个基于聚合函数的条件,无需子查询

云捷
2023-03-14

我不确定是否有比user order by和rownum(在Oracle中)更优雅的方法来解决这个问题,但下面是:

我有一张桌子(叫做winner):

Name     Salary     House   Kids
--------------------------------
Barabara 2500.00    40      4
Dale     2000.00    60      3
Aaron    2000.00    45      2
Joe      2000.00    45      4
Jacob    2000.00    50      4
Melissa  2500.00    50      4

房屋是指房屋面积(平方米)。

我需要一个查询(没有子查询)来找到“获胜者”(名称,但行可以包含更多列)。“获胜者”定义如下:

  • 工资最低
  • (如系:)有最小的房子
  • (在另一种情况下:)有最多的孩子

在这个例子中,获胜者是乔,他挣2000英镑,房子大小为45英镑,有4个孩子。

唯一的方法(它有一个非常简单但有效的代码,只包含索引,并且仍然有一种子查询(内联),即有另一个选择)是:

select * 
from 
    (select name 
     from winner
     order by salary, house, kids desc)
where rownum = 1;

没有子查询还有其他方法吗?(可能是聚合函数?)

共有2个答案

赵智勇
2023-03-14

如果您在12c上,请尝试仅提取第一行。

详见本文:https://oracle-base.com/articles/12c/row-limiting-clause-for-top-n-queries-12cr1

示例如下所示:

SELECT val
FROM   rownum_order_test
ORDER BY val DESC
FETCH FIRST 5 ROWS ONLY;

       VAL
----------
        10
        10
         9
         9
         8

5 rows selected.

SQL>
严子默
2023-03-14

在Oracle的早期版本中,您可以使用keep:

select max(name) keep (dense_rank first order by salary, house, kids desc) as name,
       max(salary) keep (dense_rank first order by salary, house, kids desc) as name,
       max(house) keep (dense_rank first order by salary, house, kids desc) as name,
       max(kids) keep (dense_rank first order by salary, house, kids desc) as name
from rownum_order_test;

如果你想要领带,你也可以试试:

select listagg(name, ',') keep (dense_rank first order by salary, house, kids desc) as names 
from rownum_order_test;

在处理相关子查询时,此构造非常有用,因为Oracle中的相关子句的作用域有限。注意,当获取值时

正如Bulat所提到的,在Oracle 12c中还有一种更好的方法,即只提取前1行。另外,还有另一种方法,使用第一个值()和选择不同的值。这两种方法都不能解决关系。

 类似资料:
  • 问题内容: 如何以方便的方式选择表中的所有列和聚合函数? 也就是说,我有一个包含100列的表格,我想发送以下内容 谢谢! 问题答案: 要从表中选择所有列,请执行以下操作: 要从表中选择一个最大值是 两者结合: 如果要在结果行中省略column44并且仅具有maxcol44,则必须列出这些列:

  • 问题内容: 我正在创建一个SQL查询,该查询将基于两个聚合函数的值从表中提取记录。这些聚合函数从同一张表中提取数据,但过滤条件不同。我遇到的问题是,与仅包含一个SUM函数的情况相比,SUM的结果要大得多。我知道我可以使用临时表创建此查询,但是我只是想知道是否有一个仅需要单个查询的优雅解决方案。 我创建了一个简化版本来演示该问题。表结构如下: 这是查询: 任何见识将不胜感激。 问题答案: 编辑: 没

  • data.table,我们可以根据行号或条件选择行: 但是,我不能同时选择行数和条件: 这可能是因为在这种格式下没有被解释为行号。我知道我可以链接这两个条件: 但是我想为这个子集分配新的列值 现在,它只为中间链接的 data.table 创建了列。我可以保存中间表,然后合并回原始表,但那会很麻烦。 实际上,我经常觉得 需要一个正确的行号。一个依赖于组的动态数字,但我想要一个可以识别每一行的唯一ID

  • 问题内容: 我的存储过程有问题。 我收到错误消息: 无法对包含聚合或子查询的表达式执行聚合功能 这是我认为发生错误的存储过程的一部分: 谢谢你。 问题答案: 如果您无论如何都要避免相关的子查询,通常可以得到更好的性能: 假设在Products表中最多只能有一个匹配项(Products,而不是Table_Products- 当然是一个表,因此不要在名称中加上该匹配项)。换句话说,如果product是

  • 问题内容: 我试图从一个列中选择最大值,同时按具有多个重复值的另一个非唯一id列进行分组。原始数据库如下所示: 使用以下方法可以很好地工作: 它返回一个像这样的表: 我希望能够在不影响GROUP BY函数的情况下添加其他列,以将诸如name和type之类的列包括到输出表中,例如: 但是它总是输出一个错误,说我需要在select语句中使用聚合函数。我应该怎么做呢? 问题答案: 您遇到了每组最多的问题