函数LAG <n>中的动态n(变量)SAS_part2

时间:2018-11-28 14:01:38

标签: sas sas-macro

您是否知道如何在函数LAGn(variable)中使用n来引用程序中的另一个宏变量->在我的情况下由V1

   data example1;
input V1 value V2;
datalines;
a 1.0 2.0
a 1.0 1.0
a 1.0 1.0
b 1.0 1.0
b 1.0 1.0
;       

proc sql;
  select max(V2) format = 1. into :n
  from example1;
quit;

data example1;
  set example1;
  by V1;
  lagval=lag&n(V2);
  run;

来自user667489的代码,适用于一列。 现在n个按V1进行更改。 我希望:

          MAX LAG
a 1.0 2.0  2  .
a 1.0 1.0  2  .
a 1.0 1.0  2  2
b 1.0 1.0  1  .
b 1.0 1.0  1  1
;    

2 个答案:

答案 0 :(得分:1)

忘记LAG()。只需添加一个计数器变量并加入该变量即可。

让我们修复示例数据步骤,使其起作用。

data example1;
  input V1 $ value V2;
datalines;
a 1 2
a 1 1
a 1 1
b 1 1
b 1 1
;

现在在每个BY组中添加唯一的行ID。

data step1;
  set example1;
  by v1;
  if first.v1 then row=0;
  row+1;
run;

现在只需将此数据集与其自身连接。

proc sql ;
 create table want as
   select a.*,b.v2 as lag_v2
   from (select *,max(v2) as max_v2 from step1 group by v1) a
   left join step1 b
   on a.v1= b.v1 and a.row = b.row + a.max_v2
 ;
quit;

结果:

Obs    V1    value    V2    row    max_v2    lag_v2

 1     a       1       2     1        2         .
 2     a       1       1     2        2         .
 3     a       1       1     3        2         2
 4     b       1       1     1        1         .
 5     b       1       1     2        1         1

希望您的实际用例比本示例更具意义。

答案 1 :(得分:0)

LAG<n>函数是一个固定深度的就地堆栈,它特定于其代码使用位置,从而在调用时具有步状态。堆栈具有深度,不能在运行时动态更改。

可以使用哈希对象在SAS DATA步骤中实现动态滞后。双重DOW技术可以对一个组进行测量,然后对其进行操作。

示例代码

此示例使用a定义一个hash对象,该对象维护组中一组值。第一个DOW循环计算成为动态堆栈高度的字段的最大值。第二个DOW循环迭代该组并检索滞后值,同时还为将来的项目滞后建立堆栈。

* some faux data;

data have (keep=group value duration);
  do group = 1 to 10;
    limit = ceil(4 * ranuni(6));
    put group= limit=;
    do _n_ = 1 to 8 + 10*ranuni(123);
      value = group*10 + _n_;
      duration = 1 + floor(limit*ranuni(123));
      output;
    end;
  end;
run;

* dynamic lag provided via hash;

data want;
  if _n_ = 1 then do;
    retain index lag_value .;
    declare hash lag_stack();
    lag_stack.defineKey('index');
    lag_stack.defineData('lag_value');
    lag_stack.defineDone();
  end;

  do _n_ = 1 by 1 until (last.group);
    set have;
    by group;
    max_duration = max(max_duration, duration);
  end;

  * max_duration within group is the lag lag_stack height;

  * pre-fill missings ;
  do index = 1-max_duration to 0;
    lag_stack.replace(key: index, data: .);
  end;

  do _n_ = 1 to _n_;
    set have;
    lag_stack.replace(key: _n_, data: value);
    lag_stack.find(key: _n_ - max_duration);
    output;
  end;

  drop index;
run;

另一种技术将涉及固定长度的环形阵列而不是哈希堆栈,但是在使用该阵列编码DATA步骤之前,您需要计算所有组的最大延迟。