Oracle - 以每组的第一行为条件

Oracle - conditional on first row of each group

编辑 - 在 Oracle 11 和 12 上。

假设我有:

ID | Name | Type
----------------
1  | AAA  | 1
2  | AAA  | 2
3  | AAA  | 3
4  | BBB  | 2
5  | BBB  | 3
6  | CCC  | 1
7  | CCC  | 2

我只想 return 一个不同的 Names 列表,其中 Type = 1 像这样:

Name | Type
-----------
AAA  | 1
CCC  | 1

我找不到 select 每个名称的第一个条目的类型为 1 的名称的方法。

使用DISTINCT.

SELECT DISTINCT name, type
FROM yourtable
WHERE type = 1

"select the names where the first entry for each name has a type of 1"

我们假设 ID 表示输入顺序。因此,我们想要找到所有记录,其中每个 NAME 的 ID 最低的记录的 TYPE = 1.

此方法使用分析函数 ROW_NUMBER() 对 TYPE 和 NAME 的出现进行评分。它适用于 11g 和 12c。

with subq as (
    select name
           , type
           , row_number() over (partition by name order by id) as rn
    from your_table
   )
select name
       , type
from subq
where type = 1
and rn = 1

下一个方法仅适用于 12c。包括在内是因为 MATCH_RECOGNIZE 是一些很酷的新语法,它可能在大量数据上表现更好。 Find out more

select name, type
from your_table
     match_recognize (
         partition by name
         order by id
         measures first (type1.id) as t1_id
         all rows per match
         pattern ( ^type1 )
         define 
               type1 as type = 1

此示例中不需要 MEASURES 子句,但在调试时将 t1_id 包含在投影中很有用,以确认查询正在返回我们期望的行。