SAS中的双循环

时间:2015-05-08 20:22:50

标签: sas

这个问题可能微不足道,但我卡住了。

我的问题是我要去每个文件夹寻找数据集并转置数据。

我编写了以下代码并且工作正常。

OPTIONS MPRINT MLOGIC SYMBOLGEN;

%LET LOC=E:\folder;

%macro test1(k,l);

libname libary "&loc.\&k\&l.";

data dataset_&l.;
set libary.dataset_original;
run;


proc transpose data=dataset_&l. out=dataset_&l._T;
run;

%mend;

%test1(var_1,var'_1);
%test1(var_2,var'_2);
%test1(var_3,var'_3);

此代码的问题是它在文件夹结构方面不是动态的。例如。如果还有4个额外的文件夹,我要写"%test1(var_3,var'_3);" 4次。

所以我尝试编写以下代码以使其更具动态性。但不幸的是它没有用。任何人都可以告诉我我在哪里弄错了。

OPTIONS MPRINT MLOGIC SYMBOLGEN;

%LET LOC=E:\folder;

%let k=var_1 var_2 var_3;

%let l=var'_1 var'_2 var'_3;

%macro words(string);
  %local count word;
  %let count=1;
  /* The third argument of the %QSCAN function specifies the delimiter */
  %let word=%qscan(&string,&count,%str( ));
  %do %while(&word ne);
    %let count=%eval(&count+1);
    %let word=%qscan(&string,&count,%str( ));
  %end;
  %eval(&count-1)
%mend words;

%macro test1(k,l);

libname libary "&loc.\&k\&l.";

data dataset_&l.;
set libary.dataset_original;
run;


proc transpose data=dataset_&l. out=dataset_&l._T;
run;

%mend;


%macro test();

%do i=1 %to %words(&k.);
%do j=1 %to %words(&l.);
%let var=%scan(&k.,&i.,str());
%let var1=%scan(&l.,&j.,str());
%test1(&var.,&var1.);

%end;
%end;

%mend;

%test();

谢谢!

1 个答案:

答案 0 :(得分:3)

试试这个:

/* Set your base directory */
%let base = E:\Folder;

/* Pipe output from dir */
filename flist pipe "dir /s /b /a:-h &base";

/* Read files from pipe */
data files;
    length file dir $ 200 name $ 50 ext $ 10;

    infile flist;
    input @1 file $ &;

    /* File extension */
    ext = scan(file, -1, ".");

    /* File name */
    name = scan(scan(file, -1, "\"), 1, ".");

    /* Directory */
    rfile = reverse(file);
    dir = reverse(substr(rfile, index(rfile, "\") + 1));

    /* Select only SAS datasets */
    if upcase(ext) = "SAS7BDAT" then output;

    drop rfile;
run;


/* Define a macro to process each file */
%macro trans_file(dir, name);

    libname d "&dir";

    proc transpose data = d.&name out = d.&name._t;
    run;

    libname d clear;

%mend trans_file;


/* Run on all files */
data _null_;
    set files;
    call execute(cats('%trans_file(', dir, ",", name, ");"));
run;

通过提交Windows command dir获取文件列表。它获取指定目录及其子目录中的所有文件。

然后,此方法使用一个简单的宏来定义数据库,从库中读取数据集,将转置的数据集写入其中,然后清除它。使用call execute为列表中的每个文件调用宏。