【问题标题】:Overwriting/Appending sas variable覆盖/附加 sas 变量
【发布时间】:2017-11-20 09:45:15
【问题描述】:
%let rows = "";

%macro test;

 proc sql noprint;
   select count(ID)
   into: sqlRows
   from mytbl;
 quit;

 %do i = 1 %to &sqlRows; * loop from 1 to sqlRows;

   proc sql noprint;
     select ID
     into: ColumnID
     from mytbl(firstobs= &i);
   quit;

   %if &rows eq "" %then %do
     %let rows = "<tr><td>&ColumnID</td></tr>";
   %end;

   %if &rows ne "" %then %do
     %let rows = "&rows<tr><td>&ColumnID</td></tr>";
   %end;

 %end;*End loop;

%mend;

%test;

%put &rows;

你好我想把mytbl的列ID数据的所有数据放到一个变量中。

我创建了一个名为 rows 的变量并在其中分配了空值。然后使用循环我逐个获取值 mytab 并将它们保存在 columnID 变量中。如果 rows 变量为空,则仅将 tr 和 td 添加到 columnID 数据。如果 rows 变量不为空,则追加它。但它只给了我表的最后一条记录。

假设 mytbl 在 ID 列中有数据 1,2 和 3

rows 变量的数据应该为

   <tr><td>1</td></tr><tr><td>2</td></tr><tr><td>3</td></tr>

但它只向我显示最后一行的数据

<tr><td>3</td></tr>

【问题讨论】:

  • 我看不到您在哪里创建任何变量。您似乎只是试图将数据放入宏变量中。将数据保存在实际数据集中可能更容易。您打算如何处理这些数据?看起来像 HTML 代码,你打算写一个 HTML 文件吗?

标签: sql sas sas-macro


【解决方案1】:

您遇到了一些不同的问题,首先是缺少分号。更重要的是,您的代码比它需要的更复杂。您可以使用 SELECT INTO: 一个 PROC SQL 步骤获得您想要的结果,您不需要为每条记录单独的 PROC SQL 步骤。玩弄:

data have;
  do ID=1 to 3;
    output;
  end;
run;

proc sql noprint;
  select cats('<tr><td>',ID,'</td></tr>') 
    into :Rows
    separated by ""
  from have;
quit;

%put &rows;

【讨论】:

    【解决方案2】:

    我认为您严重误解了 SAS 中的宏变量是什么,而不是常规变量。你没有确切地说出你最终会用这个做什么,但尽管如此。

    首先,宏变量不带引号;如果它们包含它们,它们将被视为常规字符。所以:

    %let var = "";
    %let var = "&var.123";
    %put &=var.;
    

    会回来

    """123"
    

    因为它对引号知之甚少(它有点知道它们,但它不像普通 SAS 变量那样对待它们)。

    其次,正如 Quentin 正确指出的那样,您到底为什么要使用 SQL 一次执行一行?这基本上与您使用 SQL 的原因相反。 SQL 非常适合一次对整个数据集执行某些操作,一次只处理一行绝对是可怕的——这就是数据步骤的用途。

    如果你真的想要一个 SAS 变量,或者你想一次处理一行,你应该只使用数据步骤:

    data want;
      set mytbl end=eof;
      retain rows;  *do not need to initialize to missing, that is normal;
      length rows $32767;
      rows = cats(rows,"<tr><td>",ColID,"</td></tr>");
      if eof then output;
    run;
    

    如果您打算使用 call execute,通常会这样做,例如,如果您计划将 put 用于 HTML 页面(例如在存储过程中),其中包含您想要执行的一些包装器代码,在if _n_=1 开始,if eof 结束。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2018-09-27
      • 2017-02-25
      • 2021-08-24
      • 2020-09-30
      • 2015-12-04
      • 2013-06-06
      • 2018-02-27
      相关资源
      最近更新 更多