我正在尝试使用PARMBUFF宏来重复具有20个不同客户端定义的数据步骤(下面的一个示例)。
DATA _NULL_;
%GLOBAL bank1;
%LET bank1 = O.OWNER LIKE 'XXXXX%';
RUN;
数据步骤将创建由上面创建的客户端宏变量定义的单独表。
%MACRO CLIENTBUILD/PARMBUFF;
%LET N=%SYSFUNC(COUNTW(&SYSPBUFF,%STR(,)));
%DO I=1 %TO &N;
%LET CLIENT=%SCAN(%QSYSFUNC(COMPRESS(%BQUOTE(&SYSPBUFF),%STR(%(%)))),&I,%STR(,));
CREATE TABLE CLIENT AS
SELECT DISTINCT C.DATE,
C.TIME,
C.RELEASE,
C.TASK
FROM CALLS C
INNER JOIN OWN_GRNT O ON SUBSTR(C.TASK,1,9)= O.TASK
AND &CLIENT
;
%END;
%MEND;
我想用宏的NAME(String)创建这个表...但是我在引用表的名称的宏字符串时遇到了问题。 我尝试按如下方式重新格式化宏(为了尝试并使用
调出表的名称的宏的字符串/名称)%MACRO CLIENTBUILD/PARMBUFF;
%LET N=%SYSFUNC(COUNTW(&SYSPBUFF,%STR(,)));
%DO I=1 %TO &N;
%LET CLIENT=%SCAN(%QSYSFUNC(COMPRESS(%BQUOTE(&SYSPBUFF),%STR(%(%)))),&I,%STR(,));
CREATE TABLE '&CLIENT' AS
SELECT DISTINCT C.DATE,
C.TIME,
C.RELEASE,
C.TASK
FROM CALLS C
INNER JOIN OWN_GRNT O ON SUBSTR(C.TASK,1,9)= O.TASK
AND &CLIENT
;
%END;
%MEND;
Then calling the macro out with –
PROC SQL;
%CLIENTBUILD(&NCT);
QUIT;
但这会导致错误:
ERROR: The value &CLIENT is not a valid SAS name.`
是否有解决方案来调出依赖于用于定义客户端的宏变量的宏标题?一旦解决,我想用....创建每个客户端数据集
Proc SQL;
%CLIENTBUILD(&bank1,&bank2,&bank3,..........);
QUIT;
答案 0 :(得分:3)
首先,一个建议。不要以这种方式构建您的应用程序。这是一个非常混乱和冒险的方法。您正在使用应该是参数的全局宏变量,并且您正在尝试文本解析这些宏变量的名称列表。
以这种方式编写宏:
%macro maketable(table=,where=);
proc sql;
create table &table. as
...
where &where.;
quit;
%mend maketable;
然后从存储WHERE子句的数据集中构造对%maketable
的调用(我假设这不仅仅是开放代码?如果是,请通过excel将其放入数据集中。)
proc sql;
select cats('%maketable(table=',tablename,',where=%nrstr(',whereclause,'))'
into :tablecall separated by ' '
from my_whereclause;
quit;
然后在下一行添加&tablecall.
,当您运行它时,您将获得所有表格。
(顺便说一句,你可能甚至不能制作20张桌子,但是制作1张桌子,其中20个值是变量 - 但是你没有解释你在这之后做了什么,所以很难告诉。)
如果必须这样做,您需要了解宏变量解析的工作原理。有关此问题的解释,请参阅my answer here,或有关此主题的my SGF paper。 SAS文档也非常擅长解释这一点。
基本上,您需要单独解析表名&table
以定义表名,然后多次解析它以获取where子句。
以下是使用sashelp.class的示例。
%let abc= age gt 13;
%let def= age lt 13;
%let ghi= age eq 13;
%macro doit/parmbuff;
%LET N=%SYSFUNC(COUNTW(&SYSPBUFF,%STR(,)));
%DO I=1 %TO &N;
%LET CLIENT=%SCAN(%QSYSFUNC(COMPRESS(%BQUOTE(&SYSPBUFF),%STR(%(%)))),&I,%STR(,));
%PUT &=CLIENT;
proc sql;
create table &client. as
select * from sashelp.class
where &&&client.;
quit;
%end;
%mend doit;
%doit(abc,def,ghi);
&&&client
将&client
解析为abc
,然后在那里留下&符号(&abc
) - 然后解析,然后将&abc
解析为value(where子句)。
答案 1 :(得分:0)
您不需要为此类应用程序使用PARMBUFF。只是不要使用逗号作为分隔符。例如,您可以使用空格或|如下例所示。
%macro doall(list);
%local i item ;
%do i=1 %to %sysfunc(countw(&list,|));
%let item=%scan(&list,&i,|);
... process current item ...
%end;
%mend doall ;
%doall(A|B|C|D);