我有一系列文件,每个文件都包含SQL代码。我想使用SAS来运行使用该SQL的直通查询。由于这些文件经常更改,我只是想要一种自动化的方法来保持SAS与这些文件同步。我在想,如果我能导入SQL文件,并把它放入一个宏变量,那么我就可以使用宏在我的SAS直通和一切将是同步的。但我不知道如何在SAS数据集以外的任何地方读取外部SQL,这不会有很多意义开始…例子:sqlcode.sql
select *
from table1
在SAS: /*Somehow read sqlcode.sql into a macro variable sassql*/
proc sql;
connect to netezza (SERVER=MYSERVER DATABASE=MYDBS);
execute (
&sassql.
) by netezza;
;
quit;
edit -新答案:
您可以通过数据步骤将整个查询读入宏变量,但是查询中的字符总数将被限制为32,767个,因为这是字符变量所能容纳的最大字符数。
我建议使用数据步骤逐行读取查询,将整个查询放入临时文件中,并使用%include
:
filename query temp;
data _null_;
infile 'C:My Documentssql query.sql' end=eof truncover;
input @1 line $32767.;
file query;
if _n_=1 then put 'proc sql;
connect to netezza (SERVER=MYSERVER DATABASE=MYDBS);
execute (';
put line;
if eof then put ') by netezza;
quit;';
run;
%include query / source2;
filename query clear;
这里,临时文件是"query", data步骤逐行读取sql文件,并将每一行输出到临时文件。
用datasteps读取文件,然后使用sql select-into查询,如下所示:
data query_text;
infile 'sql query.sql';
input line $1000;
run;
proc sql;
select * from query_text into :sassql separated by ' ';
quit;
整个读入文件将被转储到一个宏变量
我已经遇到这个问题几次了,所以我写了我自己的%include
宏版本%include_file()
。看看我的笔记,它应该工作,虽然如果你包括的文件包含宏令牌,你可能需要调整宏引用功能。
它可以在任何大小的文件上工作(因为它一次读取一行,而不是试图将整个文件存储到一个变量中)。
就像这样调用它:
proc sql;
connect to netezza (SERVER=MYSERVER DATABASE=MYDBS);
execute (
%include_file(iFileName=c:mypathmysasfile.sas);
) by netezza;
;
quit;
代码如下。我建议把它放在你的宏自动调用库:
%macro include_file(iFileName=);
%local filrf rc fid rc2;
%let filrf=myfile2;
%let rc=%sysfunc(filename(filrf, &iFileName, , lrecl=32767));
%let fid=%sysfunc(fopen(&filrf,i,32767,b));
%if &fid > 0 %then %do;
%let rc = %sysfunc(fread(&fid));
%do %while(&rc eq 0);
/* NOTE THE STACKED COMMANDS BECAUSE WE ARE RETURNING THE CONTENTS OF MACRO VAR C HERE AND DONT WANT WHITESPACE */
%let rc2=%sysfunc(fget(&fid,c,32767));%quote(&c)%let rc = %sysfunc(fread(&fid));
%end;
%end;
%else %do;
%put C &fid %sysfunc(sysmsg());
%end;
%let rc=%sysfunc(fclose(&fid));
%let rc=%sysfunc(filename(filrf));
%mend;