2016-11-15 26 views
2

我有以下表格:轉換行到列的連接

declare @Risks table(id int identity, name varchar(20)) 
declare @Mitigations table(id int identity, riskId int, mitigation_desc varchar(20), record_date datetime) 

insert into @Risks(name) 
select 'Risk 1' union all 
select 'Risk 2' union all 
select 'Risk 3' 

insert into @Mitigations(riskId, mitigation_desc, record_date) 
select 1, 'Mitigation 1', '2016-01-01' union all 
select 1, 'Mitigation 2', '2016-01-01' union all 
select 2, 'Mitigation 3', '2016-01-01' 

SELECT * 
FROM @Risks a 
LEFT OUTER JOIN @Mitigations b ON a.id = b.riskId 

每個風險都可以有超過1減緩,是沒有限制的,我想要做的是能夠顯示所有各風險緩解水平是這樣的:

ID Name mitigation_desc  record_date mitigation_desc record_date 
--- ----- ------------------ ------------- ---------------- ------------- 
1 Risk 1 Mitigation 1  2016-01-01 Mitigation 2  2016-01-01 
2 Risk 2 Mitigation 3  2016-01-01 NULL    NULL 
3 Risk 3 NULL    NULL   NULL    NULL 

我曾嘗試使用樞軸幾個場景和加入,但他們都不是作爲風險可以有緩解的數量不夠靈活。有沒有其他的方式來實現這一點?

爲了使事情更容易,我可以限制顯示的緩解數量,例如總是顯示每組風險3組緩解。

感謝

+3

你在哪裏顯示這些數據?這似乎更像是一個演示問題,而不是數據提取問題。 – iamdave

+0

這是發送到.net mvc應用程序 – 03Usr

+1

簡短的答案是「否」。 SQL需要你知道有多少列*(和它們的名字等)*被提前*返回。你的兩個選擇是編寫寫入SQL *的代碼(查詢你的表以確定你需要多少列,然後生成你需要應對這種情況的SQL)*。或者*(這是更好的選擇,因爲它適合標準化的RDBMS模式)*只需返回表而不進行透視,然後將其轉到您的應用程序/報告圖層中。 *(一般的經驗法則是演示文稿問題不應該在您的數據層中解決。)* – MatBailie

回答

1

如果你只想最多兩個緩解的回報,那麼我會使用以下...

WITH 
    sorted_risks AS 
(
    SELECT 
     ROW_NUMBER() OVER (PARTITION BY riskID 
           ORDER BY record_date, 
             mitigation_desc) AS ordinal, 
     * 
    FROM 
     @risks 
) 
SELECT 
    riskID, 
    MAX(CASE WHEN ordinal = 1 THEN mitigation_desc END) AS mitigation_desc_1, 
    MAX(CASE WHEN ordinal = 1 THEN record_date  END) AS record_date_1, 
    MAX(CASE WHEN ordinal = 2 THEN mitigation_desc END) AS mitigation_desc_2, 
    MAX(CASE WHEN ordinal = 2 THEN record_date  END) AS record_date_2 
FROM 
    sorted_risks 
WHERE 
    ordinal <= 2 
GROUP BY 
    riskID 

如果你想要最新的兩(而不是最古老二)記錄,將ORDER BY record_date,更改爲ORDER BY record_date DESC,

即便如此,我仍然認爲SQL是做錯的地方。

你的意見建議你只是爲了演示的原因在MVC應用程序中這樣做。在這種情況下,您應該在MVC應用程序的表示層中執行此操作。

+0

非常好,謝謝你的答案和指針。 – 03Usr