获取第一个电话号码的行

时间:2016-03-25 10:11:31

标签: sql oracle

我需要每页显示100个成员。由于会员的电话号码多,我必须为每个会员选择第一个电话号码。

以下是查询成员的每个电话号码的查询:

    SELECT * FROM 
    (     
          SELECT
          row_number() over(order by(1)) rn, 
          NAME, PHONE    
                FROM MEMBERS t0     
                LEFT OUTER JOIN MEMBER_IDENTITY ON MEMBER_IDENTITY.ID=t0.ID 
                LEFT JOIN MEMBER_PHONE ON MEMBER_PHONE.MEMBER_ID=t0.ID    
                WHERE
          NAME LIKE 'U%' 
          ORDER BY NAME ASC 
    )      
WHERE rn >= 0
AND rn <= 100

我如何选择第一个 - 或MAX,等电话号码?

2 个答案:

答案 0 :(得分:1)

您可以进行子查询以检索电话号码及其每个成员的行号,然后过滤掉其中的第一个:

SELECT  * 
FROM    (
        SELECT    row_number() OVER (ORDER BY name ASC) rn, 
                  name, 
                  phone
        FROM      members t0 
        LEFT JOIN member_identity 
               ON member_identity.id = t0.id 
        LEFT JOIN (
                  SELECT member_id,
                         phone
                         row_number() OVER (PARTITION BY member_id ORDER BY (1)) ph_rn
                  FROM   member_phone
                  ) member_phone
               ON member_phone.member_id = t0.id
              AND ph_rn = 1
        WHERE     name LIKE 'U%' 
        ORDER BY  name ASC
        )
WHERE   rn BETWEEN 0 AND 100

我会:

  • 使用相同的顺序将rn值确定为结果集(ORDER BY name ASC),否则订单在各页之间将不一致;
  • 在外BETWEEN条件中使用WHERE,但第一页不需要下限条件(0)。

答案 1 :(得分:1)

当您切换到MAX时,您可以直接在名称上应用ROW_NUMBER(在 GROUP BY / HAVING之后,窗口化聚合函数被计算):

SELECT * FROM 
 (     
      SELECT
         row_number() over (ORDER BY NAME ASC) rn, 
         NAME, MAX(PHONE)    
      FROM MEMBERS t0     
      LEFT OUTER JOIN MEMBER_IDENTITY ON MEMBER_IDENTITY.ID=t0.ID 
      LEFT JOIN MEMBER_PHONE ON MEMBER_PHONE.MEMBER_ID=t0.ID    
      WHERE NAME LIKE 'U%'
      GROUP BY NAME 
 )      
WHERE rn >= 0
AND rn <= 100

或将聚合移动到派生表中:

SELECT * FROM 
 (     
      SELECT
         row_number() over (ORDER BY NAME ASC) rn, 
         NAME, PHONE    
      FROM MEMBERS t0     
      LEFT OUTER JOIN MEMBER_IDENTITY ON MEMBER_IDENTITY.ID=t0.ID 
      LEFT JOIN
       ( SELECT MEMBER_ID, MAX(PHONE) AS PHONE
         FROM MEMBER_PHONE
         GROUP BY NAME
       ) MEMBER_PHONE
      ON MEMBER_PHONE.MEMBER_ID=t0.ID    
      WHERE NAME LIKE 'U%'         
 )      
WHERE rn >= 0
AND rn <= 100