SAS - 在If语句中循环吗?

时间:2012-11-30 19:45:46

标签: arrays sas do-loops

我一直在使用SAS一年,我终于开始使用数组,宏,以及所有那些很酷的东西。

我想做什么:

我有一个合并的数据集,其中包含测试中不同年级学生的数据。我需要为每个年级创建不同的文件。我没有等级变量来轻松地对数据集进行排序并创建不同的文件。我确实有一个特定于每个年级的变量索引。

示例 - 我所拥有的:

+-------+--------+--------+--------+--------+--------+
|  ID   | sc_132 | sc_139 | sc_142 | sc_143 | sc_151 |
+-------+--------+--------+--------+--------+--------+
| 16623 | 1      | 1      | 0      | .      | .      |
| 16624 | 1      | 0      | 0      | .      | .      |
| 16626 | 1      | 1      | 1      | .      | .      |
| 17221 | .      | .      | .      | 1      | 0      |
| 17222 | .      | .      | .      | 0      | 1      |
| 17225 | .      | .      | .      | 0      | .      |
+-------+--------+--------+--------+--------+--------+

示例 - 我想要的:

+-------+--------+--------+--------+--------+--------+
|  ID   | sc_132 | sc_139 | sc_142 | sc_143 | sc_151 |
+-------+--------+--------+--------+--------+--------+
| 16623 | 1      | 1      | 0      | .      | .      |
| 16624 | 1      | 0      | 0      | .      | .      |
| 16626 | 1      | 1      | 1      | .      | .      |
+-------+--------+--------+--------+--------+--------+
+-------+--------+--------+--------+--------+--------+
|  ID   | sc_132 | sc_139 | sc_142 | sc_143 | sc_151 |
+-------+--------+--------+--------+--------+--------+
| 17221 | .      | .      | .      | 1      | 0      |
| 17222 | .      | .      | .      | 0      | 1      |
| 17225 | .      | .      | .      | 0      | .      |
+-------+--------+--------+--------+--------+--------+

我在哪里:

我有很多特定于每个等级的变量,有些变量包含缺失的数据,所以要彻底检查所有等级特定的变量并输出包含任何这些字段中的数据的任何观察结果。我可以用一个可怕的长IF那么声明......

DATA grade1 grade2 grade3 grade4;
SET gradeall;
    IF sc_132 ^= . OR sc_139 ^= . OR (AND SO ON FOR ABOUT 34 VARIABLES) THEN OUTPUT grade1;
RUN;

但我认为这是使用数组的好时机。我找不到任何关于何时何地可以使用do循环的简单解析文档。使用我的其他编程语言的逻辑和我浏览过的循环,我把以下内容放在一起。

%let gr1_var = sc_132 sc_139 sc_142;
/*-GRADE SPECIFIC ARRAY REPEATED FOR OTHER GRADES -*/

DATA grade1 grade2 grade3 grade4;
SET gradeall;
PUT &gr1_var;
ARRAY grade1 [*] &gr1_var;
IF (
    DO i= 1 TO (DIM(items5_all)-1);
        items5_all(i) ^=. OR ;
    END;
    DO i= DIM(items5_all);
        items5_all(i) ^=.;
    END;
    )
THEN OUTPUT grade1;
    /*-IF THEN STATEMENT THEN REPEATED FOR OTHER GRADES-*/
run;

我希望这会给我相当于上面的长IF THEN声明,而不必输入它。但当然它是无功能的。

你甚至可以在If语句中使用do循环(我还没有找到任何这方面的例子)? 有没有人对如何完成这项任务有任何建议?

1 个答案:

答案 0 :(得分:2)

我认为如果您只想输出任何包含任何特定字段数据的观察,您只需要执行sum数组。如果任何观察值没有变量值,则总和为空,因此不会输出该观测值。不需要循环。就像:

 %let gr1_var = sc_132--sc_142; /*for array definition, you may use "--" or "-" */
 %let gr2_var = sc_143 sc_151;

 DATA grade1 grade2;
 SET gradeall;
 ARRAY grade1 [*] &gr1_var;
 ARRAY grade2 [*] &gr2_var;
 if sum(of grade1(*))^=. then output grade1;
 if sum(of grade2(*))^=. then output grade2;
 run;

顺便说一句,如果在这里使用宏,则不需要编写多个if..then和数组定义。

我认为你不能在DO语句中使用if..else LOOP,就像你放在这里一样。