0

我有表格來測試我需要透視的得分數據,但我被困在如何去做。SQL Server 2008數據透視表沒有聚集

我擁有的數據是:

gradelistening speaking reading writing 
0 0.0 0.0 0.0 0.0 
1 399.4 423.8 0.0 0.0 
2 461.6 508.4 424.2 431.5 
3 501.0 525.9 492.8 491.3 
4 521.9 517.4 488.7 486.7 
5 555.1 581.1 547.2 538.2 
6 562.7 545.5 498.2 530.2 
7 560.5 525.8 545.3 562.0 
8 580.9 548.7 551.4 560.3 
9 602.4 550.2 586.8 564.1 
10 623.4 581.1 589.9 568.5 
11 633.3 578.3 598.1 568.2 
12 626.0 588.8 600.5 564.8 

但我需要這樣的:

gr0 gr1 gr2 gr3 gr4 gr5 gr6 gr7 ... 
listening 0.0 399.4 461.6 501.0 521.9 555.1 562.7 560.5 580.9... 
speaking 0.0 423.8... 
reading 0.0 0.0 424.2... 
writing 0.0 0.0 431.5... 

我並不需要聚合任何東西,只是透視數據。

+0

等級的數量是固定的(在本例中是12/13)還是可變的? – Dan 2010-03-22 16:47:14

+0

是的,等級的數量是固定的。當分數不可用時,數據集將填充零記錄,因此查詢總是有13條記錄。 – 2010-03-22 16:48:27

回答

2

以下是解決問題的一種方法,但我不確定它是否最有效。

DECLARE @PivotData table(grade int, listening float, speaking float, reading float, writing float) 
INSERT into @PivotData 
SELECT 0, 0.0, 0.0, 0.0, 0.0 UNION ALL 
SELECT 1, 399.4, 423.8, 0.0, 0.0 UNION ALL 
SELECT 2, 461.6, 508.4, 424.4, 431.5 UNION ALL 
SELECT 3, 501.0, 525.9, 492.8, 491.3 

SELECT TestType, [0] As gr0, [1] as gr1, [2] as gr2, [3] as gr3 
FROM 
(
    SELECT grade, TestType, score 
    FROM 
    (
     SELECT grade, listening, speaking, reading, writing from @PivotData 
    ) PivotData 
    UNPIVOT 
    (
     score for TestType IN (listening, speaking, reading, writing) 
    ) as initialUnPivot 
) as PivotSource 
PIVOT 
(
    max(score) FOR grade IN ([0], [1], [2], [3]) 
) as PivotedData 

基本上我所做的就是最初unpivot的數據,以獲取包含的檔次,testtype表,並在自己的列各得分,那麼我轉動數據得到你想要的答案。事實上,我的UnPivoted源數據包含TestType列,因此每個組合的等級和測試類型都會返回單個分數,因此所有聚合將僅返回該組合的特定分數,並且不會對其執行任何操作。

我只在前四個年級完成了這個練習,但我確信你可以告訴你需要添加什麼來讓它在所有13個年級都能正常工作。

+0

謝謝。這工作。我只是簡單地將「從@PivotData」改爲我的表名,並在它後面添加了一個WHERE子句,並且一切順利。在其餘的成績中加入沒有問題。 – 2010-03-22 19:55:49

+0

@布賴恩劉易斯,很高興我一切都解決了。 – 2010-03-22 20:06:30

0

這是一個解決方案。下面的代碼使用Oracle的雙表爲這些區域創建一個虛擬表(例如,聽,說等)。然而,對於SQLServer,我相信你可以在每個聯合中截斷'from dual'子句。該查詢執行笛卡爾積,以便將列爲導向的成績下拉到標準化結構(列技能,等級和分數)。然後以正常方式使用這些數據來轉發數據。我還添加了「排名」列,以便根據您指定的結果對數據進行排序。

select skill, rank 
    , max(case grade when 0 then score else null end) gr0 
    , max(case grade when 1 then score else null end) gr1 
    , max(case grade when 2 then score else null end) gr2  
from (
    select skill, rank, grade 
    , case skill when 'listening' then listening 
       when 'speaking' then speaking 
       when 'reading' then reading 
       when 'writing' then writing end score 
    from tmp_grade t, (
    select 'listening' skill, 1 rank from dual 
    union (select 'speaking', 2 from dual) 
    union (select 'reading', 3 from dual) 
    union (select 'writing', 4 from dual) 
) area1 
) 
group by skill, rank 
order by rank;