SAS-使用动态宏变量创建数据步长变量
我想使用call symput将数据步骤变量的实例存储在宏变量中,然后在同一数据步骤中使用该宏变量填充新字段,每36条记录为其分配一个新值 我尝试了以下代码:SAS-使用动态宏变量创建数据步长变量,sas,Sas,我想使用call symput将数据步骤变量的实例存储在宏变量中,然后在同一数据步骤中使用该宏变量填充新字段,每36条记录为其分配一个新值 我尝试了以下代码: data a; set a; if MOB = 1 then do; MOB1_accounts = accounts; call symput('MOB1_acct', MOB1_accounts); end; else if MOB > 1 then MOB1_accounts = &MOB1_acct.;
data a;
set a;
if MOB = 1 then do;
MOB1_accounts = accounts;
call symput('MOB1_acct', MOB1_accounts);
end;
else if MOB > 1 then MOB1_accounts = &MOB1_acct.;
run;
我有一系列重复的暴徒(1-36)。我想创建一个名为MOB1_Accts的字段,将其设置为MOB=1的队列的#个帐户,并在MOB=2、3、4等时保留该值。我基本上希望每36条记录“向下拖动”MOB 1值
出于某种原因,此宏变量返回“1”而不是正确的#帐户。我认为这可能是一个字符/数字问题,但不确定。我已经尝试了单引号、双引号、符号等各种可能的排列方式。。。不走运
谢谢你的帮助 您误用了宏系统 源代码中的符号(
&
)介绍人告诉SAS解析以下符号并将其放入代码提交流中。因此,在运行数据步骤中,无法更改已解析的&MOB1\u账户。换句话说,正在运行的步骤不能更改其源代码——解析的宏变量对于该步骤的所有隐式迭代都是相同的,因为其值已成为该步骤源代码的一部分
您可以使用SYMPUT()
和SYMGET()
函数将字符串移出或移入数据步骤。但这仍然是解决问题的错误方法
最直接的技术可能是
- 使用
retain
ed变量
mod(\n\u36)
计算以确定每36行。(\u n
是一个简单步骤中的行号代理,只需一个集合。)
例如:
data a;
set a;
retain mob1_accounts;
* every 36 rows change the value, otherwise the value is retained;
if mod(_n_,36) = 1 then mob1_accounts = accounts;
run;
您没有显示任何数据,因此实际需要的程序语句可能略有不同
对比SYMPUT/SYMGET
与RETAIN
如上所述,SYMPUT/SYMGET
是一种通过关闭宏符号表中的存储来保留值的可能方法。不过还是有处罚的。SYM*
需要一个函数调用和任何正在进行的阴谋/黑盒操作来存储/检索符号值,还可能需要在字符和数字之间进行额外的转换
例如:
data a;
set a;
retain mob1_accounts;
* every 36 rows change the value, otherwise the value is retained;
if mod(_n_,36) = 1 then mob1_accounts = accounts;
run;
读取1000000行<代码>数据_null
避免将写入开销作为对比度的一部分的步骤
data have;
do rownum = 1 to 1e6;
mob + 1;
accounts = sum(accounts, rand('integer', 1,50) - 10);
if mob > 36 then mob = 1;
output;
end;
run;
data _null_;
set have;
if mob = 1 then call symput ('mob1_accounts', cats(accounts));
mob1_accounts = symgetn('mob1_accounts');
run;
data _null_;
set have;
retain mob1_accounts;
if mob = 1 then mob1_accounts = accounts;
run;
在我的系统日志上
142 data _null_;
143 set have;
144
145 if mob = 1 then call symput ('mob1_accounts', cats(accounts));
146
147 mob1_accounts = symgetn('mob1_accounts');
148 run;
NOTE: There were 1000000 observations read from the data set WORK.HAVE.
NOTE: DATA statement used (Total process time):
real time 0.34 seconds
cpu time 0.34 seconds
149
150 data _null_;
151 set have;
152 retain mob1_accounts;
153
154 if mob = 1 then mob1_accounts = accounts;
155 run;
NOTE: There were 1000000 observations read from the data set WORK.HAVE.
NOTE: DATA statement used (Total process time):
real time 0.04 seconds
cpu time 0.03 seconds
或
由于某些原因,我的呼叫symput+symget/symgetn仍然只返回“1”。但retain语句工作得非常好。我不知道我怎么直到现在才听说它-非常感谢!