2014-06-17 48 views
3

我的SQL非常生鏽。我試圖改變這個表:根據第三列中的類型代碼將列拆分爲兩列

+----+-----+--------------+-------+ 
| ID | SIN | CONTACT | TYPE | 
+----+-----+--------------+-------+ 
| 1 | 737 | [email protected] | email | 
| 2 | 760 | 250-555-0100 | phone | 
| 3 | 737 | 250-555-0101 | phone | 
| 4 | 800 | 250-555-0102 | phone | 
| 5 | 850 | [email protected] | email | 
+----+-----+--------------+-------+ 

到這個表:

+----+-----+--------------+-------------+ 
| ID | SIN | PHONE  | EMAIL | 
+----+-----+--------------+-------------+ 
| 1 | 737 | 250-555-0101 | [email protected] | 
| 2 | 760 | 250-555-0100 |    | 
| 4 | 800 | 250-555-0102 |    | 
| 5 | 850 |    | [email protected] | 
+----+-----+--------------+-------------+ 

我寫此查詢:

SELECT * 
    FROM (SELECT * 
      FROM people 
     WHERE TYPE = 'phone') phoneNumbers 
     FULL JOIN (SELECT * 
        FROM people 
        WHERE TYPE = 'email') emailAddresses 
      ON phoneNumbers.SIN = emailAddresses.SIN; 

主要生產:

+----+-----+--------------+-------+------+-------+-------------+--------+ 
| ID | SIN | CONTACT | TYPE | ID_1 | SIN_1 | CONTACT_1 | TYPE_1 | 
+----+-----+--------------+-------+------+-------+-------------+--------+ 
| 2 | 760 | 250-555-0100 | phone |  |  |    |  | 
| 3 | 737 | 250-555-0101 | phone | 1 | 737 | [email protected] | email | 
| 4 | 800 | 250-555-0102 | phone |  |  |    |  | 
| |  |    |  | 5 | 850 | [email protected] | email | 
+----+-----+--------------+-------+------+-------+-------------+--------+ 

我知道我可以選擇我想要的列,bu SIN列不完整。我似乎記得,我應該第三次加入表格來獲得完整的SIN列,但我不記得如何。

如何生成我的目標表(ID,SIN,PHONE,EMAIL)?

編輯和澄清:我非常感謝迄今爲止收到的答案,但作爲一個SQL新手,我不熟悉您正在使用的技術(case語句,條件聚合和透視)。這不能使用JOIN和SELECT來完成嗎?請原諒我對這件事的無知。 (這並不是說我不感興趣的卓越技術,但我不想太快太早移動。)接近,這是有條件的聚集

+0

我搞砸了這一段時間,唯一可以爲此工作的其他事情將是多個UNIONs,這可能無法正常工作的情況下。最簡單的選擇是使用CASE,它只是SQL的IF循環。 – tsHunter

回答

3

方式一:

select min(ID), SIN, 
     max(case when type = 'phone' then contact end) as phone, 
     max(case when type = 'email' then contact end) as email 
from people t 
group by sin; 
1

似乎是一個pivot(神諭.com)在這裏很容易工作。

SELECT ID, SIN, PHONE, EMAIL 
FROM PEOPLE 
PIVOT (
    MAX(CONTACT) 
    FOR TYPE IN ('EMAIL', 'PHONE') 
) 
0

我意識到這是比張貼的所有解決方案不太優雅,但在這裏它是無論如何,只使用JOIN,然後選擇一個解決方案:

SELECT sins.SIN, phone, email 
    FROM ((SELECT SIN email_sin, contact email 
      FROM people 
      WHERE TYPE = 'email') email 
     FULL JOIN (SELECT SIN phone_sin, contact phone 
        FROM people 
        WHERE TYPE = 'phone') phone 
      ON email.email_sin = phone.phone_sin) 
     RIGHT JOIN (SELECT DISTINCT SIN FROM people) sins 
      ON sins.SIN = phone_sin OR sins.SIN = email_sin; 

這缺少ID列。