我正在尝试以二进制形式转换分类变量(Product),然后想知道每个客户有多少产品。
数据采用以下格式:
ID Product
C1 A
C1 B
C2 A
C3 B
C4 A
我用于将类别转换为二进制文件的代码
IF PRODUCT="A" THEN PROD_A =1 ; ELSE PROD_A=0;
IF PRODUCT="B" THEN PROD_B =1 ; ELSE PROD_B=0;
TOT_PROD = SUM(PROD_A, PROD_B);
但是当我算不上时。对于所有客户,它给我'1'的产品,我期待1或2。
我试过了
TOT_PROD = PROD_A + PROD_B;
但我得到的结果相同
答案 0 :(得分:4)
这都在一个datastep里面,对吗?如果是这样,您一次只处理一行。对于每个单独的行,PROD_A和PROD_B的唯一可能值是1或0。你需要一个聚合函数。例如,如果您的数据集名为PRODUCTS
:
DATA X;
SET PRODUCTS;
IF PRODUCT="A" THEN PROD_A = 1 ; ELSE PROD_A=0;
IF PRODUCT="B" THEN PROD_B = 1 ; ELSE PROD_B=0;
TOT_PROD = SUM(PROD_A, PROD_B);
RUN;
(TOT_PROD
在X
中总是等于1,但现在没关系。)
现在总结一下:
proc sql;
create table prod_totals as
select product, sum(tot_prod) as total_products
from x
group by product;
quit;
更简单地说就是跳过数据步骤:
proc sql;
create table prod_totals as
select product, count(*) as total_products
from products
group by product;
quit;
或使用PROC SUMMARIZE
或PROC MEANS
代替PROC SQL
。
答案 1 :(得分:0)
要在数据步骤中执行此操作,您需要retain
。确保首先对数据集by id
进行了排序。
data prod_totals;
set products;
by ID;
retain prod_a prod_b;
if first.id then do; *initialize to zero for each new ID;
prod_a=0; prod_b=0;
end;
if product='A' then prod_a=1; *set to 1 for each one found;
else if product='B' then prod_b=1;
if last.id then do; *for last record in each ID, output and sum total;
total_products=sum(prod_a,prod_b);
output;
end;
keep id prod_a prod_b total_products;
run;
答案 2 :(得分:0)
我假设你只想要每个id 1个记录输出。
在下面的解决方案中,我使用了DOW-Loop(DO-Whitlock)。
如果您希望prod_a
和prod_b
只是为了帮助总计,如果输出中不需要它们,那么您可以使用以下内容:
data want;
do until(last.id);
set have;
by id;
tot_prod=sum(tot_prod,product='A',product='B');
end;
run;
如果输出中需要prod_a
和prod_b
,那么您可以使用:
data want;
do until(last.id);
set have;
by id;
prod_a=(product='A');
prod_b=(product='B');
tot_prod=sum(tot_prod,prod_a,prod_b);
end;
run;
在两个数据步骤中,每个id的最后一个产品将与其他变量一起输出,而在第二个数据步骤示例的情况下,最后一个prod_a&每个id的prod_b也将被输出。