i有10个变量(var1-var10),我需要在SAS中重命名var10-var1。因此,基本上,我需要将VAR10重命名为VAR1,VAR9 VAR2,VAR8 VAR3等。
这是我基于本文使用的代码,http://analytics.ncsu.edu/sesug/2005/ps06_05.pdf:
%macro new;
data temp_one;
set temp;
%do i=10 %to 1 %by -1;
%do j=1 %to 10 %by 1;
var.&i=var.&j
%end;
%end;
;
%mend new;
%new;
我遇到的问题是它仅将var1重命名为var10,因此do-loop中的最后一次迭代。
事先感谢您的任何帮助!
Emily
您真的不需要这样做,可以用列表引用重命名变量,尤其是在依次命名的情况下。
IE:
rename var1-var10 = var10-var1;
这是一个证明这一点的测试:
data check;
array var(10) var1-var10 (1, 2, 3, 4, 5, 6, 7, 8, 9, 10);
output;
run;
data want;
set check;
rename var1-var10 = var10-var1;
run;
如果您确实出于某种原因需要手动进行操作,则需要两个数组。一旦分配了变量,就丢失了旧变量,因此无法再访问它。因此,您需要某种临时数组才能保持新值。
虽然Reeza的答案是正确的,但值得一试,为什么您的方法不起作用 - 这是另一个合理的方法,如果是令人费解的,则是这样做的。
首先,您有一些次要的语法问题,例如放错的半隆,错误的时期(它们 end end end not oken nob stem stem shem)以及缺少的运行语句;我们会忽略这些并在更改代码时修复它们。
第二,当您真的不想要它时,您会有两个嵌套循环。您不想对i
的每次迭代(总共100倍)进行10次内部代码(每次迭代一次j
);您想对i
和j
的每次迭代进行一次内部代码。
让我们看看这个修复程序是什么给我们的:
data temp;
array var[10];
do _n_ = 1 to 15;
do _i = 1 to 10;
var[_i] = _i;
end;
output;
end;
drop _i;
run;
%macro new();
data temp_one;
set temp;
%do i=10 %to 1 %by -1;
%let j = %eval(11-&i.);
var&i.=var&j.;
%end;
run;
%mend new;
%new();
好吧,所以现在这更接近您想要的东西;但是你有一个问题,对吗?您失去了下半年的值(嗯,实际上是自使用%by -1
以来的上半年),因为它们没有存储在单独的地方。
您可以通过拥有一个临时垃圾区域来进行此操作,在该区域上进行原始变量,使您可以同时更改值并访问原始变量。一种基于数组的常见方法(而不是基于宏)的方法。
在宏中的外观。%macro new();
data temp_one;
set temp;
%do i=10 %to 1 %by -1;
%let j = %eval(11-&i.);
_var&i. = var&i.;
var&i.=coalesce(_var&j., var&j.);
%end;
drop _:;
run;
%mend new;
我们使用返回第一个不遗赠参数的coalesce()
;在前五个迭代中,它使用var&j.
,但第二次迭代使用_var&j.
。而不是使用此函数,您也可以仅预填充变量。
一个更好的选择是使用rename
,就像Reeza在上述答案中所做的那样,但在这里提出的内容更像是您的原始答案:
%macro new();
data temp_one;
set temp;
rename
%do i=10 %to 1 %by -1;
%let j = %eval(11-&i.);
var&i.=var&j.
%end;
;
run;
%mend new;
这起作用是因为rename
实际上并没有移动事物 - 它只是设置了"请将此值写出到输出上的_____变量"的值。
这实际上是链接论文提出的作者,我怀疑您只是错过了rename
位。这就是为什么您在整个过程之后拥有单个分号的原因(因为它只是一个rename
语句,所以只有一个;
),而不是每次迭代后的单个分号(就像您需要分配需要的那样)。