SAS宏数组创建变量的DROP语句失效问题求助
SAS宏DROP语句警告问题解决
问题描述
运行代码计算各变量时间序列的斜率时,为复用逻辑处理其他函数,需删除数组创建的变量,但输出数据集仍保留ys_new&i._:类变量,同时收到警告:
The variable 'ys_new3_:'n in the DROP, KEEP, or RENAME list has never been referenced
推测是%do %while循环的迭代器i最终被计算为3导致该问题。
问题原因
循环结束后,迭代器i的值会比实际处理的参数个数多1。例如本次处理了2个参数(N_TRX和TRANSACTION_AMT),循环结束时i变为3,导致DROP语句中的ys_new&i._:被解析为ys_new3_:,但该变量从未创建,因此触发警告。
解决方案
在循环内部构建需要DROP的变量列表,每次迭代将当前创建的ys_new&i._:加入列表,最终统一DROP整个列表,避免迭代器值异常导致的无效变量名。
修正后完整代码
DATA HAVE; INPUT ID N_TRX_M0-N_TRX_M12 TRANSACTION_AMT_M0-TRANSACTION_AMT_M12; DATALINES; 1 3 6 3 3 7 8 6 10 5 5 8 7 7 379866 856839 307909 239980 767545 511806 603781 948936 566114 402214 844657 2197164 817390 2 51 56 55 73 48 57 54 53 55 52 49 72 53 6439314 7367157 4614827 9465017 3776064 3661525 7870605 3971889 4919128 10024385 4660264 7748467 7339863 3 5 . . . . . . . . . . . . 232165 . . . . . . . . . . . . ; RUN; %Macro slope(variables)/parmbuff; %let i = 1; %let drop_list = ; /* 初始化需要DROP的变量列表 */ /* 获取第一个参数 */ %let parm_&i = %scan(&syspbuff,&i,%str( %(, %))); %do %while (%str(&&parm_&i.) ne %str()); array ys&i(12) &&parm_&i.._M12 - &&parm_&i.._M1; array ys_new&i._[12]; %let drop_list = &drop_list ys_new&i._:; /* 将当前ys_new变量加入DROP列表 */ /* 处理缺失值*/ k = 1; do j = 1 to 12; if not(missing(ys&i(j))) then do; ys_new&i._[k] = ys&i[j]; k + 1; end; end; nonmissing = n(of ys_new&i._{*}); xbar = (nonmissing + 1)/2; if nonmissing ge 2 then do; ybar = mean(of ys&i(*)); cov = 0; varx = 0; do m=1 to nonmissing; cov=sum(cov, (m-xbar)*(ys_new&i._(m)-ybar)); varx=sum(varx, (m-xbar)**2); end; slope_&&parm_&i. = cov/varx; end; %let i = %eval(&i+1); /* 获取下一个参数 */ %let parm_&i = %scan(&syspbuff ,&i, %str( %(, %))); %end; drop &drop_list k j m nonmissing ybar xbar cov varx; /* 统一DROP所有临时变量 */ %mend; %let var_slope = N_TRX, TRANSACTION_AMT ; DATA FEATURES; SET HAVE; %slope(&var_slope) RUN;
说明
修正后的宏通过drop_list变量动态收集所有需要删除的临时变量,确保DROP语句仅包含实际创建的变量,彻底消除警告,同时保持代码的复用性,适配任意数量的输入参数。
内容的提问来源于stack exchange,提问作者Sandra Guerrero
相关产品推荐
相关产品推荐

