如何使用预先指定的变量格式编写从csv文件创建SAS数据集的%宏?

时间:2016-05-15 12:25:17

标签: sas

如何使用现有SAS数据集的格式导入SAS中的csv以及如何从此过程创建宏?

假设我设法从具有方便格式的数据集中的5个csv文件加载数据。现在我定期发布这些文件的新版本(v2,v3,...),我想在新数据集中加载数据,格式与旧数据相同。

如何为此编写宏?

2 个答案:

答案 0 :(得分:1)

一种简单的方法是

  1. 使用proc contents
  2. 检查现有数据集的结构
  3. 使用proc import
  4. 从新到达的文件中读取数据
  5. 从日志文件
  6. 复制proc import生成的数据步骤
  7. 修改它以符合所需的结构(格式)
  8. 使用一些宏变量进行参数化
  9. 制作宏的这些宏变量参数。
  10. 或者在Enterprise Guide

    中向程序添加一些提示

    例如,假设proc contents data=mydata; run;为您提供了其他信息

    Alphabetic List of Variables and Attributes         
    #   Variable    Type    Len
    3   long        Char    50
    1   num         Num     8
    2   short       Char    8
    

    导入此

    num,kort,lang
    4,alfa,A short sentence
    5,beta,And another one
    

    用这个

    proc import replace
        datafile='c:\TEMP\csv_v3.csv' 
        out=myData;
        format num 8. kort $8. lang $33.;
    run;
    

    在日志中读取

    29          /**********************************************************************
    30          *   PRODUCT:   SAS
    31          *   VERSION:   9.4
    32          *   CREATOR:   External File Interface
    33          *   DATE:      15MAY16
    34          *   DESC:      Generated SAS Datastep Code
    35          *   TEMPLATE SOURCE:  (None Specified.)
    36          ***********************************************************************/
    37             data WORK.MYDATA    ;
    38             %let _EFIERR_ = 0; /* set the ERROR detection macro variable */
    39             infile 'c:\TEMP\csv_v3.csv' delimiter = ',' MISSOVER DSD lrecl=32767 firstobs=2 ;
    40                informat num best32. ;
    41                informat kort $4. ;
    42                informat lang $16. ;
    43                format num best12. ;
    44                format kort $4. ;
    45                format lang $16. ;
    46             input
    47                         num
    48                         kort $
    49                         lang $
    50             ;
    51             if _ERROR_ then call symputx('_EFIERR_',1);  /* set ERROR detection macro variable */
    52             run;
    

    您可以自定义为

    %macro importMyData(csvName);
    data WORK.MYDATA;
    /*  The first dot in &csvName..csv below closes the macro variable name, 
        so you need the second too */
        infile "c:\TEMP\&csvName..csv" 
            delimiter = ',' MISSOVER DSD lrecl=32767 firstobs=2 ;
    /*  Note the firstobs option, which skips the headers! */
    
    /*  Set the formats accordign to the output of proc contents */
        format num 8. ;
        format kort $8. ;
        format lang $50. ;
    
    /*  Potentially you need to set a few informats too 
        I left one as an example */
        informat num best32. ;
    
        input
                num
                kort $
                lang $
        ;
    run;
    %mend;
    %importMyData(csv_v3.csv);
    

答案 1 :(得分:1)

因此,如果新CSV文件的结构与现有数据集的结构相匹配,那么您应该能够拥有一个简单的程序:

data new ;
  if 0 then set old ;
  infile "new.csv" dsd firstobs=2 truncover ;
  input (_all_) (+0);
run;

您可以通过首先用宏变量替换输入数据集,模型数据集和输出数据集来将其转换为宏。

%macro readcsv(infile,out,model);
data &out;
  if 0 then set &model;
  infile "&infile" dsd firstobs=2 truncover ;
  input (_all_) (+0);
run;
%mend readcsv;

因此对宏的调用可能如下所示:

%readcsv(infile=file1_v2.csv,out=mylib.file1_v2,model=mylib.file1)

如果输入的CSV文件不符合模型,则会出现问题。因此,如果列的顺序错误,则数据将被读入错误的字段。此外,您还需要确保将关联的INFORMAT与变量(如日期和时间值)相关联,这些变量将在模型数据集中使用。

您可以通过将输入语句中的_all_替换为CSV文件中的名称列表来修复列顺序问题。但这需要名称与模型变量名称匹配。以前的版本只要求列的顺序与模型匹配。

%macro readcsv2(infile,out,model);
%local names ;
data _null_;
  infile "&infile" obs=1;
  input;
  call symputx('names',translate(_infile_,' ',','));
run;
data &out;
  if 0 then set &model;
  infile "&infile" dsd firstobs=2 truncover ;
  input (&names) (+0);
run;
%mend readcsv2;