3

一意の列値 (Val2) ごとに列値 (Val1) を個別の列として、最大 10 列で表示したいシナリオがあります。

CREATE TABLE #TEMP1 (Val1 NVARCHAR(4), Val2 NVARCHAR(10));

insert into #Temp1 Values ('S01','00731')
insert into #Temp1 Values ('S02','00731')
insert into #Temp1 Values ('S03','00731')
insert into #Temp1 Values ('S04','00731')
insert into #Temp1 Values ('S05','00731')
insert into #Temp1 Values ('S06','00731')
insert into #Temp1 Values ('S07','00731')
insert into #Temp1 Values ('S08','00731')
insert into #Temp1 Values ('S09','00731')
insert into #Temp1 Values ('S07','00731')
insert into #Temp1 Values ('S04','00741')
insert into #Temp1 Values ('S01','00746')
insert into #Temp1 Values ('S01','00770')
insert into #Temp1 Values ('S01','00771')
insert into #Temp1 Values ('S02','00771')

Val1    Val2
--------------------------
S01     00731
S02     00731
S03     00731
S04     00731
S05     00731
S06     00731
S07     00731
S08     00731
S09     00731
S07     00731
S04     00741
S01     00746
S01     00770
S01     00771
S02     00771

次に、ピボット列を使用してそれぞれの一意の Val2 値を表示し、最大 10 個の Val1 値を列として表示します。

SELECT [Val2],
c1, c2, c3, c4, c5, c6, c7, c8, c9, c10
FROM
(SELECT Val1, Val2
FROM         #TEMP1) AS PivotTable
PIVOT
(
MAX([PivotTable].[Val1])
FOR
Val1
IN
(C1, c2, c3, c4, c5, c6, c7, c8, c9, c10)
) AS PivotTable;

私は次のような結果を得たいと思っています:

Val2    c1  c2  c3  c4  c5  c6  c7  c8  c9  c10
--------------------------------------------------------------------------------------
00731  S01  S02 S03 S04 S05 S06 S07 S08 S09 S07 
00741  S04  NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL
00746  S01  NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL
00770  S01  NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL
00771  S01  S02 NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL

しかし、実際には、列のすべての NULL 値を取得するだけです:

Val2    c1  c2  c3  c4  c5  c6  c7  c8  c9  c10
--------------------------------------------------------------------------------------
00731  NULL NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL
00741  NULL NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL
00746  NULL NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL
00770  NULL NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL
00771  NULL NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL    NULL
4

2 に答える 2

2

あなたの要件は完全には明確ではありませんが、 -- という名前の新しい列を作成しようとしているcようrow_number()ですc1, c2 c3, etc

サブクエリで次を使用する場合:

SELECT Val1, Val2,
  'C'+ cast(row_number() over(partition by Val2 
                              order by val1) as varchar(10)) col
FROM TEMP1

デモで SQL Fiddle を参照してください

結果は次のようになります。

| VAL1 |  VAL2 | COL |
----------------------
|  S01 | 00731 |  C1 |
|  S02 | 00731 |  C2 |
|  S03 | 00731 |  C3 |
|  S04 | 00731 |  C4 |
|  S05 | 00731 |  C5 |
|  S06 | 00731 |  C6 |
|  S07 | 00731 |  C7 |
|  S07 | 00731 |  C8 |
|  S08 | 00731 |  C9 |
|  S09 | 00731 | C10 |
|  S04 | 00741 |  C1 |
|  S01 | 00746 |  C1 |
|  S01 | 00770 |  C1 |
|  S01 | 00771 |  C1 |
|  S02 | 00771 |  C2 |

あなたがしたい結果のようですPIVOTPIVOT次に、次を使用してこれに適用します。

SELECT Val2,
   c1, c2, c3, c4, c5, c6, c7, c8, c9, c10
FROM
(
  SELECT Val1, Val2,
    'C'+ cast(row_number() over(partition by Val2 
                                order by val1) as varchar(10)) col
  FROM TEMP1
) src
PIVOT
(
  MAX(Val1)
  FOR col IN (C1, C2, C3, C4, C5, C6, C7, C8, C9, C10)
) piv;

SQL Fiddle with Demoを参照してください。最終結果は次のとおりです。

|  VAL2 |  C1 |     C2 |     C3 |     C4 |     C5 |     C6 |     C7 |     C8 |     C9 |    C10 |
------------------------------------------------------------------------------------------------
| 00731 | S01 |    S02 |    S03 |    S04 |    S05 |    S06 |    S07 |    S07 |    S08 |    S09 |
| 00741 | S04 | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) |
| 00746 | S01 | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) |
| 00770 | S01 | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) |
| 00771 | S01 |    S02 | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) |

注: 私の結果は、値がグループ化されるORDER BY val1原因となる を実行しているため、目的の結果として要求されているものとは少し異なります。S07

S07要求しない限り、データベース内のデータの順序はありません。そのため、値の 1 つが として表示されるという保証はありませんC10。以下を使用して結果を取得できますが、結果が常に正しい順序になるという保証はありません。

SELECT Val2,
  c1, c2, c3, c4, c5, c6, c7, c8, c9, c10
FROM
(
  SELECT Val1, Val2,
    'C'+ cast(row_number() over(partition by Val2 
                                order by (select 1)) as varchar(10)) col
  FROM TEMP1
) src
PIVOT
(
  MAX(Val1)
  FOR col IN (C1, C2, C3, C4, C5, C6, C7, C8, C9, C10)
) piv;

SQL Fiddle with Demoを参照してください。を使用するorder by (select 1)とデータの順序が変更されますが、常にその順序になるとは限りません。結果は次のとおりです。

|  VAL2 |  C1 |     C2 |     C3 |     C4 |     C5 |     C6 |     C7 |     C8 |     C9 |    C10 |
------------------------------------------------------------------------------------------------
| 00731 | S01 |    S02 |    S03 |    S04 |    S05 |    S06 |    S07 |    S08 |    S09 |    S07 |
| 00741 | S04 | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) |
| 00746 | S01 | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) |
| 00770 | S01 | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) |
| 00771 | S01 |    S02 | (null) | (null) | (null) | (null) | (null) | (null) | (null) | (null) |
于 2013-02-05T15:07:28.927 に答える
1

相関サブクエリを使用してクロスタブまたはピボットを作成する標準的な方法を試し、ランキング関数 (ここでは CTE 内) を使用して、値を入れる列を決定できます。

;with cte as (
    select Val1
        , Val2
        , row_number() over (partition by Val2 order by Val1) as col
        --, row_number() over (partition by Val2 order by Id) as col -- Use this if you have an identity
    from #TEMP1
    --from (select distinct * from #TEMP1) as t -- Use this to rank distinct entries
)
select c.Val2
    , (select Val1 from cte where Val2 = c.Val2 and col = 1) as c1
    , (select Val1 from cte where Val2 = c.Val2 and col = 2) as c2
    , (select Val1 from cte where Val2 = c.Val2 and col = 3) as c3
    , (select Val1 from cte where Val2 = c.Val2 and col = 4) as c4
    , (select Val1 from cte where Val2 = c.Val2 and col = 5) as c5
    , (select Val1 from cte where Val2 = c.Val2 and col = 6) as c6
    , (select Val1 from cte where Val2 = c.Val2 and col = 7) as c7
    , (select Val1 from cte where Val2 = c.Val2 and col = 8) as c8
    , (select Val1 from cte where Val2 = c.Val2 and col = 9) as c9
    , (select Val1 from cte where Val2 = c.Val2 and col = 10) as c10
from cte as c
group by c.Val2
order by c.Val2

どの列がVal2属するかを判断するにはいくつかの方法があることに注意してください.CTEにはいくつかの可能性があります(いくつかのコメントがあります)。S07ただし、現在、10 番目の列にある必要があるかどうかを判断する方法がないため、現在の目的の出力に到達することはできません。おそらく、必要に応じて、一時テーブルに ID を追加すると、イベントの順序がキャプチャされます。その可能性もCTEに含めました。

于 2013-02-05T15:07:55.720 に答える