什么是声明在sas数据步骤中真正做的?

时间:2015-07-04 05:10:56

标签: duplicates sas datastep

好吧这看起来很简单,但是我无法解释sas datastep中的“by statement”是什么。我知道什么时候需要使用它,但我不确定它在做什么。

在下面的示例中,我了解first.var和last.var的虚拟sas列是什么时候它具有的值。是否在var initial和metal周围创建了这些虚拟列的by语句?然后sas扫描整个数据集一次?

data jewelers ;
  input id initial $ metal $ ;
datalines;
456 D Gold
456 D Silver
123 L Gold
123 L Copper
123 L PLatinum
567 R Gold
567 R Gold
567 R Gold
345 A Platinum
345 A Silver
345 A Silver
;

proc sort ;
  by initial metal ;
run;

data dups;
  set jewelers ;
  by initial metal ;                           
  if not (first.metal and last.metal) then output;
run;

如果我推销打印件,我希望如此:

567 R Gold
567 R Gold
567 R Gold
345 A Silver
345 A Silver

2 个答案:

答案 0 :(得分:2)

正如您所承认的那样,SAS正在为first.byvar声明中的每个last.byvar创建自动变量byvarby。从SAS set语句读入的记录在SAS移动到PDV之前保存在缓冲区中(程序数据向量 - 在输出之前在每一行上执行数据步骤逻辑),因此SAS可以向前看缓冲区中的下一条记录,以查看是否有任何更改的byvars,并为当前PDV中的行设置last.byvar = 1

我在你所说的你所期望的内容和你在dups数据集中得到的内容之间的唯一区别是记录的顺序 - 因为你已经按照首字母排序,然后是金属,A Silver记录在R Gold条记录之前排序。

如果要在保留原始行顺序的同时获取这两个变量的重复项,则需要记下原始记录顺序,并在第二个数据后将重复数据集重新排序到该顺序中步骤

答案 1 :(得分:0)

SAS基本上将当前记录与之前的记录进行比较,然后计算FIRST。最后。标志。如果你愿意,你可以自己动手。

data test ;
   set jewelers end=eof;
   by initial metal ;
   if not eof then 
      set jewelers (firstobs=2 keep=initial metal 
                    rename=(initial=next_initial metal=next_metal))
   ;
   first_initial = (_n_=1) or (initial ne lag(initial));
   last_initial = eof or (initial ne next_initial) ;
   first_metal = first_initial or (metal ne lag(metal)) ;
   last_metal = last_initial or (metal ne next_metal);
   put / (initial metal) (=);
   put (first:) (=);
   put (last:) (=);
run;