d*****o 发帖数: 6 | 1 小女工作中碰到一个SQL问题。。由于现在还是个SQL 菜鸟,对此问题很是挠头。。
举例
id var1 var2 var3
1 A B B
1 B C B
1 A B C
2 A A B
2 A A B
2 C C B
3 C A A
3 B A A
3 A A A
如果要写一个logic选择每个id只keep一个,条件是优先选有c的,其次是b.最后是a.
还有一点是先看var3再看var2,最后是var1
象id=1.var3里面优先选c所以要keep这个obs,其他delete
id=2,var3里面都相同,所以看var2,只有A和B情况下优先选B,所以就keep第一个
record
以此类推。。。
这个code在SQL上如何实现呢?或者在SAS可以实现的话也可以。 |
k*******a 发帖数: 772 | 2 you can create a score for each obs, then find the maximum score, for
example
data test;
input id var1 $ var2 $ var3$;
datalines;
1 A B B
1 B C B
1 A B C
2 A A B
2 A A B
2 C C B
3 C A A
3 B A A
3 A A A
;
proc sql;
select *, 100*((var3='C')*3 + (var3='B')*2 + (var3 = 'A'))
+ 10*((var2='C')*3 + (var2='B')*2 + (var2 = 'A'))
+ ((var1='C')*3 + (var1='B')*2 + (var1 = 'A')) as score,
max(calculated score) as maxscore
from test
group by id
having score = maxscore;
quit; |
l****u 发帖数: 529 | 3 proc sql;
create table two as
select *, case when min(var3)=max(var3) then ' ' else max(var3) end as id3,
case when min(var2)=max(var2) then ' ' else max(var2) end as id2,
case when min(var1)=max(var1) then '' else max(var1) end as id1
from test
group by id
having var3=id3 or(id3=' 'and var2=id2) or (id3=''and id2=''and var1=id1);
quit; |
l****u 发帖数: 529 | 4 good idea
【在 k*******a 的大作中提到】 : you can create a score for each obs, then find the maximum score, for : example : data test; : input id var1 $ var2 $ var3$; : datalines; : 1 A B B : 1 B C B : 1 A B C : 2 A A B : 2 A A B
|
d*****o 发帖数: 6 | 5 小女子在此跪谢大牛解答,
最后我的方法参考了Kirk君的scoring的方法,还是没骨气的用了sas,,掩面,,
data temp;
set test;
score=100*((var3='C')*3 + (var3='B')*2 + (var3 = 'A'))
+ 10*((var2='C')*3 + (var2='B')*2 + (var2 = 'A'))
+ ((var1='C')*3 + (var1='B')*2 + (var1 = 'A'))
proc sort data=temp;
by id descending score;
run;
data temp1;
set temp;
by id;
if first.id then output;
run;
Kirk君,求问max(calculated score) as maxscore是在每个id下的max score么。。
我试了你的code貌似不能啊。。还有having那部分不会变蓝log里报错。。。。。
【在 k*******a 的大作中提到】 : you can create a score for each obs, then find the maximum score, for : example : data test; : input id var1 $ var2 $ var3$; : datalines; : 1 A B B : 1 B C B : 1 A B C : 2 A A B : 2 A A B
|
d********h 发帖数: 2048 | 6 不用那么麻烦,
proc sort;by id descending var3 descending var2 descending var1;
data test;
set test;
if first.id then output;
run;
【在 d*****o 的大作中提到】 : 小女子在此跪谢大牛解答, : 最后我的方法参考了Kirk君的scoring的方法,还是没骨气的用了sas,,掩面,, : data temp; : set test; : score=100*((var3='C')*3 + (var3='B')*2 + (var3 = 'A')) : + 10*((var2='C')*3 + (var2='B')*2 + (var2 = 'A')) : + ((var1='C')*3 + (var1='B')*2 + (var1 = 'A')) : proc sort data=temp; : by id descending score; : run;
|
k*******a 发帖数: 772 | 7 哈对啊,就是个sort的问题,看来我想复杂了
【在 d********h 的大作中提到】 : 不用那么麻烦, : proc sort;by id descending var3 descending var2 descending var1; : data test; : set test; : if first.id then output; : run;
|
d*****o 发帖数: 6 | 8 也许是我举的例子有问题, 我现在用的不是可以按照字母排列的,这里只是用ABC代表
下。
【在 d********h 的大作中提到】 : 不用那么麻烦, : proc sort;by id descending var3 descending var2 descending var1; : data test; : set test; : if first.id then output; : run;
|
m*******g 发帖数: 3044 | 9 100*((var3='C')*3 + (var3='B')*2 + (var3 = 'A'))
是啥意思? |
k*******a 发帖数: 772 | 10 then you can use format to order the way you want
data test;
input id var1 $ var2 $ var3$;
datalines;
1 A B B
1 B C B
1 A B C
2 A A B
2 A A B
2 C C B
3 C A A
3 B A A
3 A A A
;
run;
proc format;
value $fmtest 'C' = 1
'B' = 2
'A' = 3;
run;
data test1;
set test;
var1f = put(var1, $fmtest.);
var2f = put(var2, $fmtest.);
var3f = put(var3, $fmtest.);
run;
proc sort data=test1;
by id var3f var2f var1f;
run;
data test1;
set test1;
by id;
if first.id then output;
keep id var1-var3;
run;
【在 d*****o 的大作中提到】 : 也许是我举的例子有问题, 我现在用的不是可以按照字母排列的,这里只是用ABC代表 : 下。
|