【问题标题】:Sql Pivot: Display fields verticallySql Pivot:垂直显示字段
【发布时间】:2020-06-22 18:44:21
【问题描述】:

我正在尝试创建一个查询,其中数据基本上水平显示而不是垂直显示。我相信它被称为旋转(我对此有点陌生)。考虑以下: 我可以查询一个学生的地址,他们会这样显示

ID    Email
27    jd@yahoo.com
27    johndoe47@gmail.com
27    MrDoe@hotmail.com

我宁愿数据水平显示,比如

ID  Email1          Email2               Email3
27  jd@yahoo.com    johndoe47@gmail.com  MrDoe@hotmail.com

我已经通过下面的查询为一个人完成了这项工作。

SELECT Id,
MAX(CASE WHEN rownum =1 THEN B.EMAIL_ADDRESS END) AS "Email1",
MAX(CASE WHEN rownum =2 THEN B.EMAIL_ADDRESS END) AS "Email2",
MAX(CASE WHEN rownum =3 THEN B.EMAIL_ADDRESS END) AS "Email3",
MAX(CASE WHEN rownum =4 THEN B.EMAIL_ADDRESS END) AS "Email4"
FROM MyTable B
where B.Id in (21538) 
group by B.Id

这适用于一个人,主要是因为我使用的是 rownum。在此示例中,Entry4 列下的值将为空。我知道我很接近,但我不确定如何让它为多个学生工作并停止使用 rownum。 对此的任何帮助将不胜感激。提前致谢

【问题讨论】:

    标签: sql oracle pivot


    【解决方案1】:

    如果要三个,可以使用条件聚合

    select id,
           max(case whens seqnum = 1 then email end) as email1,
           max(case whens seqnum = 2 then email end) as email2,
           max(case whens seqnum = 3 then email end) as email3
    from (select t.*, row_number() over (partition by id order by email) as seqnum
          from t
         ) t
    group by id;
    

    【讨论】:

    • 您好,我认为这效果最好。它确实以垂直方式发送电子邮件。我一直在尝试操纵查询以包括电子邮件类型。每个电子邮件地址都有一个电子邮件类型。所以它会像
    • @user1898629 。 . .只需使用type 而不是email 添加带有max() 的附加列。
    • 感谢您在此问题上的帮助。我能够生产我需要的东西
    【解决方案2】:

    如果您不关心(因为这样的东西无法扩展),请考虑listagg,它可以让您“连接”多达 4000 个字符的电子邮件地址。

    例如(请注意,第 1 - 10 行代表样本数据;您的表中已经有了它,因此您可能要考虑的查询从第 11 行开始):

    SQL> with test (id, email) as
      2    (select 27, 'jd@yahoo.com'        from dual union all
      3     select 27, 'johndoe47@gmail.com' from dual union all
      4     select 27, 'MrDoe@hotmail.com'   from dual union all
      5     --
      6     select 25, 'little@hotmail.com'  from dual union all
      7     select 25, 'foot@gmail.com'      from dual union all
      8     --
      9     select 13, 'bigfoot@net.hr'      from dual
     10    )
     11  select id,
     12    listagg(email, ', ') within group (order by email) email
     13  from test
     14  group by id
     15  order by id;
    
            ID EMAIL
    ---------- ----------------------------------------------------------------------
            13 bigfoot@net.hr
            25 foot@gmail.com, little@hotmail.com
            27 MrDoe@hotmail.com, jd@yahoo.com, johndoe47@gmail.com
    
    SQL>
    

    或者,更漂亮一点(rpad):

    <snip>
     11  select id,
     12    listagg(rpad(email, 20, ' '), ' | ') within group (order by email) email
     13  from test
     14  group by id
     15  order by id;
    
            ID EMAIL
    ---------- ----------------------------------------------------------------------
            13 bigfoot@net.hr
            25 foot@gmail.com       | little@hotmail.com
            27 MrDoe@hotmail.com    | jd@yahoo.com         | johndoe47@gmail.com
    
    SQL>
    

    【讨论】:

      【解决方案3】:

      您可以生成您的电子邮件类别(Email1、Email2 等),然后在 PIVOT 子句中使用它们。不过,请确保您将足够多的类别编码到 PIVOT 中。 (例如,使用以下查询时:如果某人有 5 个电子邮件地址,则其中一个地址不会出现在结果集中。)

      select *
      from (
        select id, email
        , 'Email' || row_number() over ( partition by id order by email ) emailcategory_
        from emailaddresses
      )
      pivot (
        max( email ) for ( emailcategory_ ) in (
          'Email1' as "Email1"  -- optional: use AS ... here to "beautify" the column headings
        , 'Email2' as "Email2"
        , 'Email3'
        , 'Email4' 
        )
      ) ;
      

      DBfiddle here.

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2012-05-02
        • 2021-10-03
        • 2012-02-25
        • 1970-01-01
        • 1970-01-01
        • 2017-12-14
        相关资源
        最近更新 更多