【发布时间】:2020-05-15 06:33:53
【问题描述】:
have 是一个 sas 数据集,包含 4 个变量:id 和变量,用于存储受访者与他们所在团队的 3 个不同成员共享的所有活动的信息。有 4 种不同的活动类型,由填充在每个玩家(p1 到 p3)的 :_activities 变量中的数字标识。以下是前 5 个 obs:
id p1_activities p2_activities p3_activities
A 1,2,3,4 1,3
B 1,3 1,2,3 1,2,3
C 1,2,3 1,2,3
D 1,2,3
E 1,2,3 1
考虑受访者 A:他们与团队中的玩家 1 共享所有 4 项活动,并与团队中的玩家 2 共享活动 1 和 3。我需要为每个玩家位置和每个活动创建标志。例如,对于所有在p1_activities 字符变量中出现2 值的受访者,一个新的数字变量p1_act2_flag 应该等于1。以下是我需要为显示的数据创建的 12 个变量中的前 6 个变量:
p1_act1_flag p1_act2_flag p1_act3_flag p1_act4_flag p2_act1_flag p2_act2_flag …
1 1 1 1 1 0 …
1 0 1 0 1 1 …
. . . . 1 1 …
. . . . 1 1 …
1 1 1 0 . . …
我现在通过在一个长度语句中初始化所有变量名来做到这一点,然后编写大量的 if-then 语句。我想使用更少的代码行,但我的数组逻辑不正确。以下是我尝试为玩家 1 创建标志的方法:
data want;
length p1_act1_flg p1_act2_flg p1_act3_flg p1_act4_flg
p2_act1_flg p2_act2_flg p2_act3_flg p2_act4_flg
p3_act1_flg p3_act2_flg p3_act3_flg p3_act4_flg
p4_act1_flg p4_act2_flg p4_act3_flg p4_act4_flg 8.0;
set have;
array plracts {*} p1_activities p2_activities p3_activities;
array p1actflg {*} p1_act1_flg p1_act2_flg p1_act3_flg p1_act4_flg;
array p2actflg {*} p2_act1_flg p2_act2_flg p2_act3_flg p2_act4_flg;
array p3actflg {*} p3_act1_flg p3_act2_flg p3_act3_flg p3_act4_flg;
array p4actflg {*} p4_act1_flg p4_act2_flg p4_act3_flg p4_act4_flg;
do i=1 to dim(plracts);
do j=1 to dim(p1actflg);
if find(plracts{i}, cats(put(j, $12.))) then p1actflg{j}=1;
else if missing(plracts{i}) then p1actflg{j}=.;
else p1actflg{j}=0;
end;
end;
*do this again for the other p#actflg arrays;
run;
由于播放器和活动数组的长度不同,我的“数组下标超出范围”,但嵌套在不同的 do-loop 中会导致我编写的代码行数比壁纸解决方案多。
您将如何更系统地和/或使用更少的代码行来做到这一点?
【问题讨论】:
标签: arrays sas indices do-loops