2017-08-26 59 views
0

我有一個看起來像這樣的數據集,我要叫它數據1:申請一個循環迭代重新編碼基於宏變量變量(調用symput/symget)

data1

我想當dv = 1時將ss,out1和out2變量的值重新編碼爲當dv = 0時每個「var」組內的值。結果數據集我想是這樣的,我們稱之爲數據2:

data2

我可以使用下面的代碼來獲得結果:

data _null_; 
    set data1; 
    if dv=0 then do; 
    if var=0 then call symput("out1_0",out1); 
    if var=0 then call symput("out2_0",out2); 
    if var=0 then call symput("ss_0",ss); 

    if var=1 then call symput("out1_1",out1); 
    if var=1 then call symput("out2_1",out2); 
    if var=1 then call symput("ss_1",ss); 

    if var=2 then call symput("out1_2",out1); 
    if var=2 then call symput("out2_2",out2); 
    if var=2 then call symput("ss_2",ss); 

    if var=3 then call symput("out1_3",out1); 
    if var=3 then call symput("out2_3",out2); 
    if var=3 then call symput("ss_3",ss); 

    if var=4 then call symput("out1_4",out1); 
    if var=4 then call symput("out2_4",out2); 
    if var=4 then call symput("ss_4",ss); 
    end; 
run; 

data data2; set data1; 
    if dv=1 then do; 
    if var=0 then out1=symget("out1_0"); 
    if var=0 then out2=symget("out1_0"); 
    if var=0 then ss=symget("ss_0"); 

    if var=1 then out1=symget("out1_1"); 
    if var=1 then out2=symget("out2_1"); 
    if var=1 then ss=symget("ss_1"); 

    if var=2 then out1=symget("out1_2"); 
    if var=2 then out2=symget("out2_2"); 
    if var=2 then ss=symget("ss_2"); 

    if var=3 then out1=symget("out1_3"); 
    if var=3 then out2=symget("out2_3"); 
    if var=3 then ss=symget("ss_3"); 

    if var=4 then out1=symget("out1_4"); 
    if var=4 then out2=symget("out2_4"); 
    if var=4 then ss=symget("ss_4"); 
    end; 
run; 

我在想,如果有一個更有效的方法來做到這一點?例如,如果「var」變量的值從0到20,而不是從0到4,那麼我想要使用一個循環來根據「var」的級數重新編碼。

任何幫助非常感謝,謝謝!

+0

爲什麼不做連接? – Reeza

+0

你能否詳細說明一下?加入哪些表? – Rosekendall

回答

1

你根本不應該使用宏變量。您可以將數據與自身結合起來,並根據DV的值選擇適當的值。

proc sql ; 
    create table data2 as 
    select a.var 
     , a.dv 
     , case when (a.dv=1) then b.out1 else a.out1 end as out1 
     , case when (a.dv=1) then b.out2 else a.out2 end as out2 
     , case when (a.dv=1) then b.ss else a.ss end as ss 
    from data1 a 
    left join (select * from data1 where dv=0) b 
    on a.var = b.var 
    ; 
quit; 

如果你確實想產生很多宏觀變量的,你可以通過VAR值動態生成的宏變量名節省大量重複編碼的。

call symputx(cats('out1_',var),out1); 
call symputx(cats('out2_',var),out2); 
call symputx(cats('ss_',var),ss); 
+0

謝謝你的迴應。我正在嘗試使用循環來使用調用symget將基於調用symput的值分配給相應的變量。我提供的代碼不是動態的,但得到了我想要的結果。我只是想通過轉置輸入數據文件,重新編碼變量,然後變回來更有效地做到這一點。我將繼續研究這個問題,看看能否在不改變數據集兩次的情況下達到我想要的結果。 – Rosekendall

+0

你的SQL代碼工作,非常感謝! – Rosekendall