2012-04-21 32 views
3

我想我越來越接近,但不知道:如何插入從列的數據,如果列B爲空,並從列B,如果A列是空

我有一個例子表包含電子郵件地址,個人和工作。 我正在嘗試創建一個包含單個地址的新表。

然後插入一個電子郵件地址,例如:如果用戶有一個工作電子郵件,但沒有個人電子郵件,插入工作電子郵件,如果沒有工作電子郵件,插入個人電子郵件。

下面的代碼不工作,但它只是展示一些我已經使用了許多變化:

使用EXAMPLE_DB

GO

CREATE TABLE USER_EMAIL(
USER_NBR CHAR(1) NOT NULL 
,EMAIL VARCHAR(30)NULL 
) 

GO 

INSERT INTO USER_EMAIL(
USER_NBR 
,EMAIL 
) 

SELECT USER_NBR 
,CASE WHEN EMAIL_ADDR IS NULL AND EMAIL_TYPE = 'Personal' THEN EMAIL_TYPE = 'Work' END EMAIL 
,CASE WHEN EMAIL_ADDR IS NULL AND EMAIL_TYPE = 'Work'  THEN EMAIL_TYPE = 'Personal' END EMAIL 
FROM EMAIL_DATA 

下面是EMAIL_DATA表:

USER_NBR EMAIL_TYPE  EMAIL_ADDR 
1   Personal 
2   Personal  [email protected] 
3   Personal   [email protected] 
4   Personal 
5   Personal   [email protected] 
1   Work   [email protected] 
2   Work   [email protected] 
3   Work 
4   Work   [email protected] 
5   Work 

謝謝大家!

+0

你可以展示'EMAIL_DATA'一些示例數據,以期望'USER_EMAIL'內容一起? – 2012-04-21 20:21:38

+0

好的,讓我編輯原文。 – Asynchronous 2012-04-21 20:23:04

+0

如果用戶同時擁有工作電子郵件和個人電子郵件,請同時插入?例如,用戶2具有兩者。 – 2012-04-21 20:32:53

回答

2

下面是一個使用row_number一個例子:

insert user_email 
     (user_nbr, email) 
select user_nbr 
,  mail.email_addr 
from (
     select user_nbr 
     ,  email_addr 
     ,  row_number() over (partition by user_nbr 
        order by 
        case 
        when email_type = 'personal' then 1 
        when email_type = 'work' then 2 
        end) as rn 
     from email_data 
     ) usr 
where usr.rn = 1 

由於只有兩個電子郵件類型,你也可以使用left join兩次:

insert user_email 
     (user_nbr, email) 
select user_nbr 
,  coalesce(pers.email_addr, work.email_addr) 
from (
     select distinct user_nbr 
     from email_data 
     ) usr 
left join 
     email_data as pers 
on  pers.user_nbr = usr.user_nbr 
     and work.email_type = 'personal' 
left join 
     email_data as work 
on  work.user_nbr = usr.user_nbr 
     and work.email_type = 'work' 

另一種方法是查找使用cross apply首選的電子郵件地址:

insert user_email 
     (user_nbr, email) 
select user_nbr 
,  mail.email_addr 
from (
     select distinct user_nbr 
     from email_data 
     ) usr 
cross apply 
     (
     select top 1 * 
     from email_data mail 
     where mail.user_nbr = usr.user_nbr 
       and mail.email_addr is not null 
     order by 
       case 
       when email_type = 'personal' then 1 
       when email_type = 'work' then 2 
       end 
     ) mail 
0

這個d oes如下:如果EMAIL_ADDR爲空,它將查看同一個表併爲同一用戶搜索另一個電子郵件類型的電子郵件。這是你想要的嗎?

INSERT INTO USER_EMAIL(
USER_NBR 
,EMAIL 
) 
SELECT e.USER_NBR 
    , EMAIL = COALESCE(e.EMAIL_ADDR 
        , (CASE e.EMAIL_TYPE 
         WHEN 'Work' THEN (SELECT TOP 1 EMAIL_ADDR 
             FROM EMAIL_DATA e1 
             WHERE e1.USER_NBR=e.USER_NBR 
             AND EMAIL_TYPE='Personal') 
         WHEN 'Personal' THEN (SELECT TOP 1 EMAIL_ADDR 
             FROM EMAIL_DATA e1 
             WHERE e1.USER_NBR=e.USER_NBR 
             AND EMAIL_TYPE='Work') 
        END)) 
FROM EMAIL_DATA e 

結果與樣品數據:

USER_NBR EMAIL 
1   [email protected] 
2   [email protected] 
3   [email protected] 
4   [email protected] 
5   [email protected] 
1   [email protected] 
2   [email protected] 
3   [email protected] 
4   [email protected] 
5   [email protected] 
+1

不確定表中是否包含「1」,「工作」,「空」或未知電子郵件被忽略的行。此外,這將插入兩行的工作和個人的電子郵件地址 – Andomar 2012-04-21 20:35:35

+0

@Andomar:我剛剛嘗試使用OP的架構。 'USER_EMAIL'只有一個電子郵件字段,所以我假設他想要兩個記錄,如果用戶提供了這兩種類型的電子郵件。 – 2012-04-21 20:38:38

+0

嗯,如果有兩行'Work',null和'Personal','joe @ hotmail.com',這個查詢會插入兩次私人郵件。可能是OP想要的,但不太可能:) – Andomar 2012-04-21 20:43:11

2

根據您的需要澄清,其中每個用戶只有一個源型或其他,這聽起來像你可以簡單地這樣做:

INSERT INTO USER_EMAIL(USER_NBR, EMAIL_ADDR) 
SELECT USER_NBR, EMAIL_ADDR 
FROM EMAIL_DATA 
WHERE EMAIL_ADDR IS NOT NULL 
+0

在示例數據中,用戶2同時具有這兩種類型的電子郵件地址 – Andomar 2012-04-21 21:13:37

+0

我問過他,他回覆了... – 2012-04-21 21:15:27

+1

啊哈!在這種情況下,這是最簡單的解決方案+1 – Andomar 2012-04-21 21:17:53

相關問題